.net 慢速SQLDataReader GetString

.net 慢速SQLDataReader GetString,.net,sqldatareader,.net,Sqldatareader,在一行上,rdr.GetString需要12-15秒 几行需要4-5秒 一些需要1-4秒 大多数行小于100毫秒 整个查询仅返回3286行,并在SSMS中在15秒内运行 [Value]是varchar600-据我所知,它没有什么特别之处 [fieldID]、[value]上有一个索引,已重建多次 在SqlDataReader中,读取第208行需要12-15秒 读取这一行所用的时间与读取所有剩余的3285行所用的时间相同 如果我将[fieldID]上的sort更改为desc,那么它将挂起在第205

在一行上,rdr.GetString需要12-15秒

几行需要4-5秒 一些需要1-4秒 大多数行小于100毫秒

整个查询仅返回3286行,并在SSMS中在15秒内运行

[Value]是varchar600-据我所知,它没有什么特别之处 [fieldID]、[value]上有一个索引,已重建多次

在SqlDataReader中,读取第208行需要12-15秒 读取这一行所用的时间与读取所有剩余的3285行所用的时间相同

如果我将[fieldID]上的sort更改为desc,那么它将挂起在第2050行 那不是同一行,甚至不是同一个[fieldID]

之前,rdr.GetString是rdr.GetByte,它从不挂起在GetByte上。 它已经有一排了! 即使使用类似但不完全相同的数据库访问另一台服务器,它也会挂起

我知道这听起来很疯狂,但它正在发生。 感觉SqlDataReader挂起了,但我一直在这个应用程序中使用SqlDataReader,返回的行比这个多得多

如果我在fieldID更改时手动执行GC.Collect,它仍然挂起在几乎相同的行上。 单个挂起的次数稍小,但总数大致相同。使用1秒的阈值可能有一个刚刚进入或刚刚离开,但问题肯定会重复

虽然它可能与挂起之间的字符数有关,但它可以低至600个,高达60000个

但这似乎与返回的数据有关。 如果我排除或包含[rownumber]而不读取它,它将挂在不同的行上。 但是这些排在同一个附近

 fieldID = rdr.GetByte(0);    // this line does not hang
 delta = sw.ElapsedMilliseconds;
 textValue = rdr.GetString(1);  // this is the line that hang on some rows 
 if ((sw.ElapsedMilliseconds - delta) > 1000L)
    Debug.WriteLine("GabeLib_Helper sw in  fields  thisFieldID = " + thisFieldID + " counter = " + counter + " ccount = " + ccount + " after getstring read delta = " + (sw.ElapsedMilliseconds - delta).ToString("N0") + " textValue = " + textValue);

select [fieldID], [value], [rowNum]
from 
(
SELECT [fieldID], ltrim(rtrim([value])) as [value]
     , ROW_NUMBER() over ( partition by [fieldID] order by ltrim(rtrim([value])) ) as [rowNum]
  FROM [docSVtext] with (nolock)
  JOIN [docFieldDef] with (nolock)
    ON [docFieldDef].[ID] = [fieldID] 
   AND [docFieldDef].[typeID] in (101) 
   AND [docFieldDef].[active] =  'true' 
   AND len(ltrim(rtrim([value]))) > 0 and len(ltrim(rtrim([value]))) <= 200 
  JOIN [docSVsys] with (nolock) 
    on [docSVsys].[sID] = [docSVtext].[sID] 
   and [docSVsys].[visibility] = 0 
 group by [fieldID], ltrim(rtrim([value]))
 ) as withRow
 where [rowNum] < 1001
 order by [fieldID], [rowNum]
下面的查询在SSMS中2秒内运行 这不是问题所在 包括以显示索引似乎正在工作

  select fieldID, value, count(*)  
  from docSVtext 
  group by fieldID, value
我跟踪了GC,它与减速无关 即使GC运行,也只需要20毫秒

delta = sw.ElapsedMilliseconds;
List<int> gcCounts = new List<int>();
for (int g = 0; g <= GC.MaxGeneration; g++) gcCounts.Add(GC.CollectionCount(g));
textValue = rdr.GetString(1);  //  " Chen, Andy </O=ENRON/OU=NA/CN=RECIPIENTS/CN=ACHEN>" + Guid.NewGuid(); //
if ((sw.ElapsedMilliseconds - delta) > 100L)
{
    Debug.WriteLine("GabeLib_Helper sw in  fields  thisFieldID = " + thisFieldID + " counter = " + counter + " ccount = " + ccount + " after getstring read delta = " + (sw.ElapsedMilliseconds - delta).ToString("N0") + " textValue = " + textValue);

}
for (int g = 0; g <= GC.MaxGeneration; g++)
{
    if (GC.CollectionCount(g) != gcCounts[g])
        Debug.WriteLine("GabeLib_Helper GC new count = " + GC.CollectionCount(g) + " old count =" + gcCounts[g] + " generation " + g + " ccount = " + ccount + " after getstring read delta = " + (sw.ElapsedMilliseconds - delta).ToString("N0"));
}

我想我知道了

如果我移除

where [rowNum] < 1001
仅查询x计数下的ID 问题是查询运行需要几秒钟的时间

我最后做的是

select top (x + 1), value 
  from table 
 where ID = i1
 group by value;
select top (x + 1), value 
  from table 
 where ID = i2
 group by value;
...
如果计数达到x+1,我就不用它了


发生的事情真的很重要,占用了很多时间,而我甚至不想要这些。即使是获得一个大计数的计数也是昂贵的

@Rhumborl,但它仍然挂在GetString上——这怎么会是一个误称呢?如果我将textValue赋值为硬编码的值,则没有问题。第一个查询是导致问题的查询吗?i、 e按字段ID排序,添加了描述的rownum?如果是,请尝试删除子查询的order by子句中的“ltrimrtrim..”。@shahkalpesh没有解决此问题。它现在挂在不同的行上。正如我所说的,查询在SSMS中运行得很好。它已经在该行上执行了rdr.GetByte0,没有问题。
select ID, count(*) 
  from table 
  ...
group by ID 
having count(*) > x
select top (x + 1), value 
  from table 
 where ID = i1
 group by value;
select top (x + 1), value 
  from table 
 where ID = i2
 group by value;
...