2012-04-24 2 views
0

現在、コードファーストでEntity Framework 4.2を使用しています。私は現在Amazon EC2上で動作するWindows 2008アプリケーションサーバーとデータベースサーバーを持っています。アプリケーションサーバーには、1日に1回実行されるWindowsサービスがインストールされています。サービスは、次のコードを実行:Entity Framework 4.2の問題コード最初にデータベースに行を追加するのに時間がかかる

// returns between 2000-4000 records 
var users = userRepository.GetSomeUsers(); 

// do some work 

foreach (var user in users) 
{ 
    var userProcessed = new UserProcessed { User = user }; 
    userProcessedRepository.Add(userProcessed); 
} 

// Calls SaveChanges() on DbContext 
unitOfWork.Commit(); 

このコードを実行するために数分かかります。また、アプリケーションサーバー上のCPUを最大限に活用します。それは、アプリケーション・サーバーの会談データベースに関連したネットワークであるかどうかを確認するために)(unitOfWork.Commitを削除

  • :私は、次の対策を試してみました。これは結果を変えなかった。
  • 私のアプリケーションサーバーをメディアインスタンスからAmazonのCPUインスタンスに変更して、リソースに関連しているかどうかを確認しました。これにより、サーバーはCPUを最大限使用しなくなり、実行時間はわずかに改善されました。しかし、実行時間はまだ数分であった。 Iは、第2及び第3のループの実行時間は同じDbContextを使用してかどうかを確認するために三回実行する上記のコードを変更した試験として

。連続するすべてのループは前のループを実行するのに時間がかかりましたが、それは同じDbContextの使用に関連する可能性があります。

何か不足していますか?これが実行するのに数分かかる単純なことが本当に可能でしょうか?私は各ループの後にデータベースにコミットしていない場合でも?これをスピードアップする方法はありますか?

答えて

1

エンティティフレームワーク(現状)は、この種の一括操作にはあまり適していません。 bulk insertメソッドの1つをEC2で使用することはできますか?そうしないと、T-SQL INSERTステートメントを手作業でコーディングする速度が大幅に向上することがあります。パフォーマンスが重要な場合は、おそらくEFを使用する利点を上回ります。

+0

Olly、すべてのユーザーをループし、各ユーザーはSQL Insert/Stored Procedureを呼び出しますか? – Thomas

+0

はい。一度にいくつかの挿入ステートメントをバッチすることができます。また、テーブルパラメータを取るspを書くことも考えられます。再度、これを使用して、いくつかの挿入をデータベースへの1回のラウンドトリップにバッチすることができます。 – Olly

+0

各行にExecuteSqlCommandを使用しようとしましたが、その違いは非常に大きかったです。実行に90分かかっていたものが3分で実行されます。 – Thomas

0

あなたのObjectContextは多くのエンティティインスタンスを蓄積していると思います。 SaveChangesには、読み込まれたエンティティの数が時間的に直線的なフェーズがあるようです。これは、それがより長くそしてより長くかかるという事実のための可能性が高いです。

これを解決する方法は、複数の小さなObjectContextを使用して古いエンティティインスタンスを取り除くことです。

関連する問題