C # 8.0 introduce tipos de referencia anulables. Aquí hay una clase simple con una propiedad anulable:
public class Foo
{
    public String? Bar { get; set; }
}¿Hay alguna manera de verificar que una propiedad de clase use un tipo de referencia anulable mediante reflexión?

[NullableContext(2), Nullable((byte) 0)]al tipo (Foo), así que eso es lo que debe verificar, ¡pero necesitaría cavar más para comprender las reglas de cómo interpretar eso!string? Xno obtiene atributos, y sestring Ypone[Nullable((byte)2)]con[NullableContext(2)]los accesosNullableContext. Si hay una mezcla, entonces seNullableusa también.NullableContextEs una optimización para tratar de evitar tener que emitir porNullabletodo el lugar.Respuestas:
Esto parece funcionar, al menos en los tipos con los que lo he probado.
Debe pasar la
PropertyInfopropiedad que le interesa y también laTypepropiedad en la que se define esa propiedad ( no un tipo derivado o primario; debe ser el tipo exacto):Vea este documento para más detalles.
La esencia general es que, o bien la propiedad en sí misma puede tener un
[Nullable]atributo, o si no lo tiene, el tipo que lo encierra podría tener un[NullableContext]atributo. Primero buscamos[Nullable], luego, si no lo encontramos, buscamos[NullableContext]en el tipo adjunto.El compilador podría incrustar los atributos en el ensamblaje, y dado que podríamos estar viendo un tipo de un ensamblaje diferente, necesitamos hacer una carga de solo reflexión.
[Nullable]podría instanciarse con una matriz, si la propiedad es genérica. En este caso, el primer elemento representa la propiedad real (y otros elementos representan argumentos genéricos).[NullableContext]siempre se instancia con un solo byte.Un valor de
2significa "anulable".1significa "no anulable" y0significa "ajeno".fuente
IBusinessRelation : ICommon {}/public interface ICommon { string? Name {get;set;} }. Si llamo al métodoIBusinessRelationcon la propiedadNameme sale falso.ICommon, noIBusinessRelation. Cada interfaz define la suyaNullableContext. Aclaré mi respuesta y agregué una verificación de tiempo de ejecución para esto.