2013-08-28 47 views
18

için toplam satır sayısı bir tablo için toplam satır sayısını almak üzere Entity Framework kullanıyorum. Sadece satır sayımını istiyorum, hayır cümlesi ya da bunun gibi bir şey. Aşağıdaki sorgu çalışır, ancak yavaştır. 4475 sayısını döndürmek yaklaşık 7 saniye sürdü.Entity Framework

Buradaki tahminim, tablonun tümünde, IEnumerable.Count() uzantı yönteminin nasıl çalıştığı gibi yinelenmesidir.

Toplam satır sayısını "hızlı" alabilmemin bir yolu var mı? daha iyi bir yolu var mı

public int GetLogCount() 
    { 
     using (var context = new my_db_entities(connection_string)) 
     { 
      return context.Logs.Count(); 
     } 
    } 
+2

nasıl içeriğini yüklemeden EntityFramework içinde satırları COUNT? http://stackoverflow.com/questions/890381/how-to-count-rows-within-entityframework-without-loading-contents – sevdalone

+3

context.Logs öğesinin bir IEnumerable değil, bir DbSet, IDbSet veya bir IQueryable olduğundan emin olun. IEnumerable ise, tüm tablo alınacak ve sayılacaktır. Bir IQueryable ise, sorgu, veritabanında "SELECT COUNT (*) dbo.Logs FRUM" gibi bir şey olacak satırları saymak için üretilecek "(Bu bir IdbSet veya DbSet ise, bir IQueryable olarak ele alınır)) – Grax

cevap

6

Satır sayınızı Entity Framework kullanarak elde etmenin yolu budur. İkinci + sorgularda muhtemelen daha hızlı performans göreceksiniz çünkü ilk çalıştırdığınız anda bir başlangıç ​​maliyeti vardır. (Ve her satırda yinelenen değil, burada Select Count() sorgusu oluşturulmalıdır).

Ham satır sayısını bir tabloda almak için daha hızlı bir yolla ilgileniyorsanız, Dapper veya OrmLite gibi bir mini ORM kullanmayı deneyebilirsiniz.

Ayrıca, tablonuzun düzgün bir şekilde tanımlandığından (en azından bir Ana Anahtar'a sahip olduğundan) emin olmalısınız, çünkü bu işlemin başarısız olması, tablodaki satırların sayılma süresini de etkileyebilir.

1

Bunu yapmak için erişiminiz varsa, bu bilgileri almak için sys tablolarını sorgulamak çok daha hızlı olacaktır.

E.g.

public Int64 GetLogCount() 
{ 
    var tableNameParam = new SqlParameter("TableName", "Logs"); 
    var schemaNameParam = new SqlParameter("SchemaName", "dbo"); 
    using (var context = new my_db_entities(connection_string)) 
    { 
     var query = @" 
      SELECT ISNULL([RowCount],0) 
      FROM (
       SELECT SchemaName, 
         TableName, 
         Sum(I.rowcnt) [RowCount] 
       FROM sysindexes I 
         JOIN sysobjects O (nolock) ON I.id = o.id AND o.type = 'U' 
         JOIN (
          SELECT so.object_id, 
            ss.name as SchemaName, 
            so.name as TableName 
           FROM sys.objects SO (nolock) 
            JOIN sys.schemas SS (nolock) ON ss.schema_id = so.schema_id 
         ) SN 
          ON SN.object_id = o.id 
       WHERE I.indid IN (0, 1) 
       AND  TableName = @TableName AND SchemaName = @SchemaName 
       GROUP BY 
         SchemaName, TableName 
      ) A 
     "; 

     return context.ExecuteStoreQuery<Int64>(query, tableNameParam, schemaNameParam).First(); 
    } 
} 
+0

MSDN, sys.partitions.rows "Bu bölümdeki yaklaşık satır sayısını gösterir." http://technet.microsoft.com/en-us/library/ms175012.aspx – cadrell0

+0

Teşekkürler, bunun yerine sysindexes kullanmak için değiştirdim. – Khan

+2

http://technet.microsoft.com/en-us/library/ms190283.aspx "Bu özellik Microsoft SQL Server'ın gelecekteki bir sürümünde kaldırılacak. Bu özelliği yeni geliştirme çalışmalarında kullanmaktan kaçının ve uygulamaları değiştirmeyi planlayın. Şu anda bu özelliği kullanın. " Ayrıca, belgelere göre, tablo bölümlenmiş ise bu işe yaramaz gibi geliyor. – cadrell0

7

Hatta aşağıda varlık çerçevesini kullanarak Ham SQL sorgusu kovabilir:

var sql = "SELECT COUNT(*) FROM dbo.Logs"; 
var total = context.Database.SqlQuery<int>(sql).Single();