문제

반사를 통해 객체의 속성을 유형 값으로 설정하고 싶습니다. string. 예를 들어, 내가 a가 있다고 가정 해 봅시다 Ship 재산이있는 클래스 Latitude,, 그것은 a double.

내가하고 싶은 일은 다음과 같습니다.

Ship ship = new Ship();
string value = "5.5";
PropertyInfo propertyInfo = ship.GetType().GetProperty("Latitude");
propertyInfo.SetValue(ship, value, null);

그대로, 이것은 던졌습니다 ArgumentException:

'System.String'유형의 객체는 'System.Double'유형으로 변환 할 수 없습니다.

값을 기준으로 적절한 유형으로 어떻게 변환 할 수 있습니까? propertyInfo?

도움이 되었습니까?

해결책

당신이 사용할 수있는 Convert.ChangeType() - 런타임 정보를 사용할 수 있습니다. IConvertible 표현 형식을 변경하려면 유형입니다. 그러나 모든 전환이 가능하지는 않지만 그렇지 않은 유형의 변환을 지원하려면 특별한 사례 논리를 작성해야 할 수도 있습니다. IConvertible.

해당 코드 (예외 처리 또는 특수 사례 로직)는 다음과 같습니다.

Ship ship = new Ship();
string value = "5.5";
PropertyInfo propertyInfo = ship.GetType().GetProperty("Latitude");
propertyInfo.SetValue(ship, Convert.ChangeType(value, propertyInfo.PropertyType), null);

다른 팁

다른 여러 사람들이 말했듯이, 당신은 Convert.ChangeType:

propertyInfo.SetValue(ship,
    Convert.ChangeType(value, propertyInfo.PropertyType),
    null);

사실, 나는 당신이 전체를 보는 것이 좋습니다 Convert 수업.

이 수업과 다른 많은 유용한 수업은 System 네임 스페이스. 나는 매년 그 네임 스페이스를 스캔하여 내가 놓친 기능을 확인하는 것이 유용하다고 생각합니다. 시도 해봐!

많은 사람들이 추천하는 것을 알았습니다 Convert.ChangeType - 이것은 어떤 경우에도 효과가 있지만 참여를 시작하자마자 nullable 받기 시작할 유형 InvalidCastExceptions:

http://weblogs.asp.net/pjohnson/archive/2006/02/07/convert.changetype-doesn_2700_t honle-nullables.aspx

래퍼는 몇 년 전에 이것을 처리하기 위해 작성되었지만 완벽하지는 않습니다.

http://weblogs.asp.net/pjohnson/archive/2006/02/07/convert.changetype-doesn_2700_t honle-nullables.aspx

유형 변환기를 사용할 수 있습니다 (오류 확인 없음) :

Ship ship = new Ship();
string value = "5.5";
var property = ship.GetType().GetProperty("Latitude");
var convertedValue = property.Converter.ConvertFrom(value);
property.SetValue(self, convertedValue);

코드 구성 측면에서 종류의 믹스 인 이는 다음과 같은 코드를 초래할 것입니다.

Ship ship = new Ship();
ship.SetPropertyAsString("Latitude", "5.5");

이것은이 코드로 달성 될 것입니다.

public interface MPropertyAsStringSettable { }
public static class PropertyAsStringSettable {
  public static void SetPropertyAsString(
    this MPropertyAsStringSettable self, string propertyName, string value) {
    var property = TypeDescriptor.GetProperties(self)[propertyName];
    var convertedValue = property.Converter.ConvertFrom(value);
    property.SetValue(self, convertedValue);
  }
}

public class Ship : MPropertyAsStringSettable {
  public double Latitude { get; set; }
  // ...
}

MPropertyAsStringSettable 다양한 클래스에 대해 재사용 할 수 있습니다.

자신만의 관습을 만들 수도 있습니다 변환기 유형 속성 또는 클래스에 첨부하려면 :

public class Ship : MPropertyAsStringSettable {
  public Latitude Latitude { get; set; }
  // ...
}

[TypeConverter(typeof(LatitudeConverter))]
public class Latitude { ... }

나는 답을 시도했다 lbushkin 그리고 그것은 훌륭하게 작동했지만 널 값과 무효 필드에는 효과가 없습니다. 그래서 나는 이것을 이것으로 변경했습니다.

propertyName= "Latitude";
PropertyInfo propertyInfo = ship.GetType().GetProperty(propertyName);
if (propertyInfo != null)
{
     Type t = Nullable.GetUnderlyingType(propertyInfo.PropertyType) ?? propertyInfo.PropertyType;
     object safeValue = (value == null) ? null : Convert.ChangeType(value, t);
     propertyInfo.SetValue(ship, safeValue, null);
}

당신은 아마도 Convert.ChangeType 방법. 예를 들어:

Ship ship = new Ship();
string value = "5.5";
PropertyInfo propertyInfo = ship.GetType().GetProperty("Latitude");
propertyInfo.SetValue(ship, Convert.ChangeType(value, propertyInfo.PropertyType), null);

사용 Convert.ChangeType 그리고 유형이 PropertyInfo.PropertyType.

propertyInfo.SetValue( ship,
                       Convert.ChangeType( value, propertyInfo.PropertyType ),
                       null );

나는 일반적인 대답으로 이것에 대답 할 것이다. 일반적으로 이러한 답변은 Guid와 함께 작동하지 않습니다. 다음은 Guids가있는 작업 버전입니다.

var stringVal="6e3ba183-89d9-e611-80c2-00155dcfb231"; // guid value as string to set
var prop = obj.GetType().GetProperty("FooGuidProperty"); // property to be setted
var propType = prop.PropertyType;

// var will be type of guid here
var valWithRealType = TypeDescriptor.GetConverter(propType).ConvertFrom(stringVal); 

또는 시도 할 수 있습니다.

propertyInfo.SetValue(ship, Convert.ChangeType(value, propertyInfo.PropertyType), null);

//But this will cause problems if your string value IsNullOrEmplty...

Metro 앱을 작성하는 경우 다른 코드를 사용해야합니다.

Ship ship = new Ship();
string value = "5.5";
PropertyInfo propertyInfo = ship.GetType().GetTypeInfo().GetDeclaredProperty("Latitude");
propertyInfo.SetValue(ship, Convert.ChangeType(value, propertyInfo.PropertyType));

메모:

ship.GetType().GetTypeInfo().GetDeclaredProperty("Latitude");

대신에

ship.GetType().GetProperty("Latitude");

다음 코드를 사용하면 문제를 해결해야합니다.

item.SetProperty(prop.Name, Convert.ChangeType(item.GetProperty(prop.Name).ToString().Trim(), prop.PropertyType));

반사로 놀고 싶습니까, 아니면 프로덕션 소프트웨어를 구축하려고합니까? 반사를 사용하여 속성을 설정하는 이유에 의문을 제기합니다.

Double new_latitude;

Double.TryParse (value, out new_latitude);
ship.Latitude = new_latitude;
라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top