Ho provato a cercare una risposta ma non sono riuscito a trovarla. Il 'problema' è semplice:Il database è bloccato quando all'interno di un foreach con linq senza ToList()
Se ho una collezione di oggetti utilizzando LINQ come segue:
var items = db.AnyTable.Where(x => x.Condition == condition).ToList();
E un'altra collezione di oggetti utilizzando LINQ, ma senza un ToList()
:
var items2 = db.AnyTable.Where(x => x.Condition == condition);
Se ora provo ad iterare ogni elemento con un foreach (non ho provato while
o altri tipi di metodi di iterazione):
foreach (var item in items)
{
int i = 2;// Doesn't matter, The important part is to put a breakpoint here.
}
Se interrompo il codice al punto di interruzione e provo ad aggiornare AnyTable
su SQL Management Studio, tutto è OK. MA SE !:
foreach (var item in items2)
{
int i = 2;// Doesn't matter, The important part is to put a breakpoint here.
}
Se adesso cerco di aggiornare (mentre sul punto di interruzione) il AnyTable
su SQL Management Studio non sarò in grado di farlo (timeout).
Perché lo ToList()
fa una tale differenza?
Da quello che ho imparato una particolare differenza è quando viene eseguita la query (su items
viene eseguito alla dichiarazione e sul items2
viene eseguito sulla dichiarazione foreach
). Perché mi impedisce di aggiornare lo AnyTable
?
Quindi l'istruzione 'foreach' crea una transazione? Wow. Un modo per impedirlo? (e che tipo di transazione crea? 'Serializable'? –
Sì, credo che sia il caso.In un semplice test ho fatto, non ho avuto problemi ad inserire da SSMS mentre l'iterazione di foreach era su un breakpoint. Puoi usare sql profiler per vedere esattamente perché la query viene bloccata –