2016-04-13 14 views
0

メソッドの実行時間が長くなるほど非常に奇妙な問題が発生しています。C#メソッドの実行時間が長くなると呼び出されます。

これは、レコードを更新する必要があるかどうかを確認する私の方法です。

public override bool NeedsUpdate(object obj) 
{ 
    BizContact contact = obj as BizContact; 

    int id = contact.ID; 

    DataRow contactRow = dbRows.FirstOrDefault(dr =>(int)dr[keyMapping.ColumnName]) == contact.ID); 
    if (contactRow == null) 
     return false; 

    DateTime localLastModified = (DateTime)contactRow["LastModified"]; 

    return contact.LastModified > localLastModified; 

} 

dbRowsコレクションは、NeedsUpdateが初めて呼び出された後にサイズが増加しないリストです。

チェックするレコードがたくさんあるため、NeedsUpdateはループで何千回も呼び出されます。

最初に呼び出されると、実行に1ミリ秒以下で十分です。

1000回の呼び出し後、このメソッドは64ミリ秒かかる。

2000回の呼び出し後、このメソッドは完了するのに138ミリ秒かかります。

3,000回の呼び出し後、このメソッドは完了するまでに187ミリ秒かかります。

dbRowsコレクションには28,000レコードが含まれているので、検索に時間がかかることはわかっていますが、少なくとも一貫性があると思います。

何が不足していると思いますか?

これは、それが使用されている方法です:あなたが探しているアイテムは、大きなリストの先頭にある場合、線形検索は、あなたが期待するよりも、実際に高速である

foreach (object obj in dataWrapper.GetObjects()) 
{ 
    // OTHER CODE 

    Stopwatch checkUpdateSW = Stopwatch.StartNew(); 
    bool needsUpdate = dataWrapper.NeedsUpdate(obj); 
    checkUpdateSW.Stop(); 

    // OTHER CODE 
} 
+3

「NeedsUpdate」で時間が費やされていますか? DataContextまたはEntityFrameworkを使用してレコードを変更している場合、エンティティの変更が増え、単一のコンテキストでトラッキングされる数が増えると、パフォーマンスが低下することがあります。 – mellamokb

+0

これは線形であり、列数が増えると増加すると予想されますが、奇妙な動作は何ですか? –

+0

あなたはクエリと同じ順序でチェックするためにあなたのレコードを持っているのですか? 'dbRows'の型は何ですか?あなたはそれを 'Dictionary'にできますか? –

答えて

2

一つのケースがあります。

可能な説明 - 各呼び出しで最初から遠いレコードを探しています。基本リストを含むサンプル:

var list = Enumerable.Range(1,10000).ToList(); 

for (var i = 0; i < 10000; i++) 
{ 
    // this linear search call will be very fast first and gradually 
    // slow down toward the end 
    var r = list.FirstOrDefaut(i); 
} 
関連する問題