2009-10-27 24 views
9

Im utilizando el PredicateBuilder como se ve aquí http://www.albahari.com/nutshell/predicatebuilder.aspx, todo funciona bien, y ahora puedo gentar LINQ dinámico a expresiones SQL, pero lo que no entiendo es por qué cuando estoy en un ciclo como este:LINQ to SQL PredicateBuilder

var inner = PredicateBuilder.False<MyType>(); 
foreach (var f in Filtermodel.InstrumentsFilterList.Where(s => s.isActive)) 
     { 
      int temp = f.InstrumentID; 
      inner = inner.Or(ud => ud.InstrumentId == temp); 
     } 

¿por qué debo utilizar esa variable temporal ?, trato de usar la "f" variable de iteración pero sólo obtener el último valor de la lista para cada iteración, como si se pasa por referencia ...

Respuesta

10

Porque PredicateBuilder está creando una expresión que se ejecutará en un momento posterior. Cuando el compilador genera el cierre para el delegado, encuentra los valores que se crean en el alcance actual y los lleva al cierre también. Dado que InstrumentID es un tipo de valor (int), inicializar y copiar el valor significa que cada delegado/cierre llevará ese valor con él. Si no crea una copia del valor cada vez, la expresión simplemente tendrá una referencia literal a f.InstrumentID, no a su valor subyacente. Entonces, más adelante, cuando la expresión se ejecuta realmente, f.InstrumentID se evalúa y saldrá como lo que se estableció por última vez, que es la última iteración.

+0

esto parece muy interesante, ¿dónde puedo obtener documentación para este tema – JOBG

2

Porque no está evaluando la condición, sino simplemente construyendo la expresión. La expresión se une a la variable definida en el foreach, que conserva su referencia a lo largo de la ejecución de todo el ciclo. Redefinirlo con una variable temporal fuerza a cada expresión a usar una variable diferente, lo que lo fuerza a referirse a la instancia con el valor en cada iteración en lugar de hacer que todas las iteraciones se refieran a la referencia individual y tengan el valor de la última iteración.

+0

gracias, esto es un poco complicado, me recuerda la vez que estaba jugando con matrices, y quiero copiar sus valores por valor .. un dolor de cabeza, tal vez en palabras simples significa que esto está haciendo una carga lenta del valor, el valor cambia con el tiempo y hay solo 1 instante de "f". – JOBG