2016-05-24 16 views
0

システムの1つに、1日あたり約20kのインサートを受け取るテーブルがあります。現在、10mの行が含まれています。私たちはシステムのアップグレードを押し出しました。このテーブルへの挿入時には(30-40sトレース)、パフォーマンスが少し遅くなっています。インサートは、一度に1つの行だけを挿入します。 - 少なくとも私の知る限り普通の大きなテーブル(EF)での挿入速度が非常に遅い

declare @generated_keys table([ID] uniqueidentifier) 

insert [dbo].[Table]([Col1], Col2], etc) 

output inserted.[ID] into @generated_keys values (@0, @1, etc) 

select t.[ID] from @generated_keys as g join [dbo].[Table] as t on g.[ID] = t.[ID] where @@ROWCOUNT > 0 

がNothing:Entity Frameworkのは、以下のSQLを生成しています。

テーブルには12個のFKがあります。エンティティが時間ベースのイベントを表すため、クラスタード・インデックスはDateCreated列にあります。さらに8つの非クラスター化インデックスがあり、さまざまな列が含まれています。 ID列はPKであり、クラスタ化されていない一意のインデックスを持ちます。

注記のとおり、省略のために、ID列はnewsequentialid()の代わりにnewid()を使用しています。

実際の実行プランは、以下の主要部分を含む:

7X 3% - 表の挿入(@generated_keys)

1X 74% - クラスタインデックスFKテーブル上

1X 8%シーク - 1つの実際の行、0.09のコスト

私は本当にこれの底に到達したいと思いますが、私はすぐに困惑しています。何かアドバイス?

+0

ClusteredIndexを削除しようとしましたか? –

+0

このテーブルのほぼすべての選択操作が日付順にデータを返すので、適切な場所にあります。また、挿入が日付順であるので、この列のクラスタード・インデックスは、PK列(uniqueidentifier)を使用するのではなく、私の目では意味がありました。 – James

+0

遅いランニングインサートは一貫しているのですか?それとも、すごく多くの時間がかかっているのですか?あなたが言ったように –

答えて

-1

お気づきのことですが、SaveChangeはレコードの挿入ごとにデータベースのラウンドトリップを行います。したがって、1日に20kレコードを追加すると、20kデータベースの往復が実行されます。

変更する&改善されたインデックスは、実際の問題がデータベースの往復の回数であるため、ほとんど違いはありません!

  • Entity Framework Extensions(すべてをサポートする&推奨)
  • EntityFramework.BulkInsert:パフォーマンスを修正するには

    、あなたはそれをサポートする3つの専攻のライブラリがあり、一括挿入に

    を実行することができますライブラリを使用する必要があります。 (サポートされていない、簡単なシナリオで作業)

  • EntityFramework.Utilities(非常に単純なシナリオでサポートされていない、仕事)

あなたはここに3つのライブラリについての詳細を学ぶことができます。 Entity Framework Bulk Insert Library Reviews & Comparisons

免責:私はプロジェクトEntity Framework Extensions

の持ち主です
+0

バルクインサートは問題ではありませんが、20kインサートは24時間のタイムスパンで発生します。一括挿入のためにそれらを保存することはオプションではありません。 – James

関連する問題