c# - propiedades - ¿Cómo saber si una propiedad es una propiedad auto-implementada con reflexión?
propiedades en programacion (2)
Entonces, en mi caso, estoy haciendo un descubrimiento de la estructura de una clase usando la reflexión. Necesito poder averiguar si una propiedad es una propiedad implementada automáticamente por el objeto PropertyInfo. Asumo que la API de reflexión no expone dicha funcionalidad porque las propiedades automáticas dependen de C #, pero ¿hay alguna solución para obtener esta información?
Esto debería hacer:
public static bool IsAutoProperty(this PropertyInfo prop)
{
return prop.DeclaringType.GetFields(BindingFlags.NonPublic | BindingFlags.Instance)
.Any(f => f.Name.Contains("<" + prop.Name + ">"));
}
El motivo es que para las propiedades automáticas, la propiedad Name
de la información de campo FieldInfo
sería:
<PropertName>k__BackingField
Dado que los caracteres <
y >
no aparecerían en los campos normales, un campo con ese tipo de denominación apunta a un campo de respaldo de una propiedad automática. Como dice Jason, todavía es frágil.
O para hacerlo un poco más rápido,
public static bool IsAutoProperty(this PropertyInfo prop)
{
if (!prop.CanWrite || !prop.CanRead)
return false;
return prop.DeclaringType.GetFields(BindingFlags.NonPublic | BindingFlags.Instance)
.Any(f => f.Name.Contains("<" + prop.Name + ">"));
}
Puede verificar si el método get
o set
está marcado con el atributo CompilerGenerated
. Luego, puede combinar eso con buscar un campo privado marcado con el atributo CompilerGenerated
contiene el nombre de la propiedad y la cadena "BackingField"
.
Quizás:
public static bool MightBeCouldBeMaybeAutoGeneratedInstanceProperty(
this PropertyInfo info
) {
bool mightBe = info.GetGetMethod()
.GetCustomAttributes(
typeof(CompilerGeneratedAttribute),
true
)
.Any();
if (!mightBe) {
return false;
}
bool maybe = info.DeclaringType
.GetFields(BindingFlags.NonPublic | BindingFlags.Instance)
.Where(f => f.Name.Contains(info.Name))
.Where(f => f.Name.Contains("BackingField"))
.Where(
f => f.GetCustomAttributes(
typeof(CompilerGeneratedAttribute),
true
).Any()
)
.Any();
return maybe;
}
No es a prueba de tontos, es bastante quebradizo y probablemente no sea portátil para, digamos, Mono.