property method constructors c# static attributes

c# - method - Pasar matriz estática en el atributo



static property c# (3)

Desafortunadamente, esto no es posible. El compilador coloca los atributos (incluidos los valores de sus argumentos) en los metadatos del ensamblado, por lo que debe poder evaluarlos en tiempo de compilación (de ahí la restricción a las expresiones constantes; la excepción para las expresiones de creación de matriz obviamente se hizo porque no podrías tener argumentos de matriz en absoluto).

Por el contrario, el código que realmente inicializa A.Months solo se ejecuta en tiempo de ejecución.

¿Es posible eludir la siguiente restricción:

Crear una matriz de solo lectura estática en una clase:

public class A { public static readonly int[] Months = new int[] { 1, 2, 3}; }

Luego páselo como un parámetro a un atributo:

public class FooAttribute : Attribute { public int[] Nums { get; set; } FooAttribute() { } }

--- Digamos que Box es una propiedad de clase A ---

[Foo(Nums = A.Months)] public string Box { get; set; }

Sé que esto no compilará y dará como resultado este error:

"Un argumento de atributo debe ser una expresión constante, tipo de expresión o expresión de creación de matriz de un tipo de parámetro de atributo".

¿Es posible sortear esto de alguna manera para poder usar la matriz estática? Pregunto, ya que será mucho más conveniente para el mantenimiento, ya que tengo muchas propiedades.

Gracias por adelantado.


No, básicamente.

Sin embargo, podría subclasificar el atributo y usarlo, es decir,

class AwesomeFooAttribute : FooAttribute { public AwesomeFooAttribute() : FooAttribute(A.Months) {} }

o:

class AwesomeFooAttribute : FooAttribute { public AwesomeFooAttribute() { Nums = A.Months; } }

y decorar con [AwesomeFoo] lugar. Si usa el reflejo para buscar FooAttribute , funcionará como se espera:

[AwesomeFoo] static class Program { static void Main() { var foo = (FooAttribute)Attribute.GetCustomAttribute( typeof(Program), typeof(FooAttribute)); if (foo != null) { int[] nums = foo.Nums; // 1,2,3 } } }

Quizás puedas anidar esto dentro de A , por lo que estás decorando con:

[A.FooMonths]

o similar


Respuesta corta: No.

Pero puede consultar la matriz int por clave:

public class A { public static readonly Dictionnary<int, int[]> NumsArrays = new[]{{1, new[]{1,1,1}}, {2, new[]{2,2,2}}, {3, new[]{3,3,3}}}; public const int Num1 = 1; public const int Num2 = 2; public const int Num3 = 3; } public class FooAttribute : Attribute { public int NumsId { get; set; } FooAttribute() { } } [Foo(NumsID = A.Num3)] public string Box { get; set; } //Evaluation: int id = (FooAttribute) Attribute.GetCustomAttribute(type, typeof (FooAttribute)); int[] result = A.NumsArrays[id];//result is {3,3,3}