2012-01-20 24 views

Respuesta

5

De MSDN - Named and Optional Parameters:

A default value must be one of the following types of expressions:

  • a constant expression;

  • an expression of the form new ValType(), where ValType is a value type, such as an enum or a struct;

  • an expression of the form default(ValType), where ValType is a value type.


typeof no devuelve necesariamente una constante de tiempo de compilación, ya que puede devolver resultados diferentes dependiendo del contexto.

+0

El tipo pasó a 'typeof' debe ser resuelto en tiempo de compilación. Por lo tanto, no puedo ver lo que quieres decir. Si lo que dices es cierto, los atributos también deberían rechazar 'constantes de tipo'. – leppie

+0

leppie, ¿qué quiere decir con "los atributos también deberían rechazar 'las constantes de tipo'"? ¿Dónde los atributos restringen valores para ser constantes? –

+1

@Fujiy - Los parámetros pasados ​​a los constructores de atributo deben ser constantes de tiempo de compilación. – Oded

4

porque no es necesariamente una expresión constante. su ejemplo presenta un typeof en una clase simple, pero ¿qué ocurre si la clase es genérica? Obviamente, esto no es constante, de lejos:

class MyClass<T> 
{ 
    public void MyMethod(Type targetType = typeof(MyClass<T>)) 
    { 
    } 
} 
11

No soy un experto IL, pero parece que se llama a un método en L_0005:

return typeof(int); 

Está el mismo de:

.maxstack 1 
.locals init (
    [0] class [mscorlib]System.Type typeofvar) 
L_0000: ldtoken int32 
L_0005: call class [mscorlib]System.Type [mscorlib]System.Type::GetTypeFromHandle(valuetype [mscorlib]System.RuntimeTypeHandle) 
L_000a: stloc.0 
L_000b: ldloc.0 
L_000c: ret 

se puede ver que no es una constante de tipo de escritura de código:

const Type constType = typeof(int); 

que devuelve un error:

Constant initialize must be compile-time constant 
+2

+1 buena manera de responder a su pregunta y probar que no es una constante de tiempo de compilación – mtijn

+0

Sin embargo, 'RuntimeTypeHandle' es una constante. – leppie

+0

RuntimeTypeHandle es una estructura. De todos modos, ¿qué es este cambio? RuntimeTypeHandle es solo el argumento del método call –

1

Isn't typeof(MyClass) a compile-time constant?

Eso particular, expresión es estáticamente resoluble, sí, pero typeof() se evalúa en tiempo de ejecución (a causa de los genéricos), por lo que la regladebe ser que una typeof() llamada no es una constante en tiempo de compilación.

Me pregunto si era en C# 1.0, cuando no había tal argumento para hacerse ...

+1

No creo que los genéricos sean la única razón para esto. Creo que es porque esto funciona: 'typeof (ClassInExternalAssembly)'. No puede resolverse hasta que se cargue el ensamblaje externo real y, por lo tanto, no es constante. – Aidiakapi

Cuestiones relacionadas