2016-09-08 55 views
5

Buduję aplikację i używam Entity Framework 6. Ale mam problemy z wykorzystaniem pamięci. Bez względu na to, co próbuję, prędzej czy później napotkam błąd braku pamięci. Do tej pory próbowałem następujące:Entity Framework 6 wykorzystanie pamięci osiąga 2 GB

  • Korzystanie z użycia w kontekście.
  • Zapisywanie zmian w partiach i usuwanie kontekstu.
  • Ręczne wywoływanie GC.Collect().

Ale żadna z nich nie uniemożliwia ramie Entity korzystania z większej ilości pamięci przy każdej operacji saveChanges, którą wykonuję. W końcu udało mi się przekroczyć limit 2 GB i zawiesiłem mój program.

Czy jest jakiś sposób, nie jestem świadomy, aby Entity Framework zwolnić całą pamięć?

Edit

using (var sqlite = new myEntities()) 
{ 
    sqlite.Configuration.AutoDetectChangesEnabled = false; 
    sqlite.Configuration.ValidateOnSaveEnabled = false; 

    foreach (var someItem in someList) 
    { 
     var newItem = new Item 
     { 
      ... 
     }; 

     sqlite.tableName.Add(newItem); 

     if (++countRecords%1000 == 0) 
     { 
      sqlite.SaveChanges(); 

     } 
    } 
    sqlite.SaveChanges(); 
} 

Jak opisano powyżej, ja też próbowałem ustawienie kontekstu bez stosowania oraz usuwania go po SaveChanges.

if (++countRecords%1000 == 0) 
{ 
    sqlite.SaveChanges(); 
    sqlite.Dispose(); 
    sqlite = new myEntities()  
} 
+2

Czy tworzysz nową instancję kontekstu dla każdego żądania do bazy danych? – Lance

+6

Aby uzyskać pomoc, musisz znaleźć sposób na stworzenie minimalnego, ale kompletnego programu, który powiela problem z pamięcią. W przeciwnym razie, jak możecie na pewno zrozumieć, wszystko, co sugerujemy, będzie czystą spekulacją. – sstan

+1

Czy możesz udostępnić swoje zapytanie EF? – Sampath

Odpowiedz

1

Jeśli to rzeczywiście kwestia partii, spróbuj coś takiego:

int batchSize = 10; 

for (int i = 0; i < = someList.Count/batchSize; i++) 
{ 
    var batch = someList.Skip(batchSize * i).Take(batchSize); 

    using (var sqllite = new nyEntities()) 
    { 
     foreach(var item in batch) 
     { 
      var newItem = new Item() {...}; 

      sqllite.tableName.Add(newItem); 
     } 

     sqllite.SaveChanges(); 
    } 
} 

ten odwraca using pozbyć się sqllite po każdej partii, a tym samym czyszcząc go i zaczynając świeży dla każdej partii .

Kod ten powstał w Notatniku ++, więc należy go wyczyścić, jeśli go wypróbujesz.

+0

Problem z seriami lub nie, bardzo podoba mi się ten przepływ, dziękuję. – BeebFreak