2009-05-22 6 views
25

私は、次のステートメントを実行している:クラスタ化インデックス更新を実行するのはなぜですか?

UPDATE TOP(1) dbo.userAccountInfo 
SET   Flags = Flags | @AddValue 
WHERE   ID = @ID; 

列 'ID' のIDENTITY制約を持つINT PRIMARY KEYです。 フラグはBIGINT NOT NULLです。

実行パスは、クラスタ化インデックス更新が実行されていることを示します。非常に高価な操作。 主キーを除き、FlagsまたはIDをカバーするインデックスはありません。私は、実際の実行パスのように感じる は次のようになります。

クラスタ化インデックスは=シーク>

+0

インデックスがクラスタ化されておらず、フィールド[フラグ]をカバーしていないことは間違いありませんか? –

+0

クエリのTOP(1)とは何ですか? – BradC

+0

@ Unknown Google: このテーブルには、非クラスタ化IDXが1つしかありません。これはIDとFlagsのどちらにも影響しません。 @ BradC: 私の声明では少し冗長です。 "このステートメントは、まったく1人のユーザーに影響します。"しかし、実際には役に立たない。 – Kivin

答えて

27

テーブルが2つの種類があります参照してください。 PRIMARY KEY制約があるため、クラスタード・インデックスが暗黙的に作成されています。このではなく、のテーブルを作成するときに余分な長さにする必要があります。クラスタ化インデックスがテーブルであるため、 'テーブル'の更新はクラスタ化インデックスの更新です。 クラスタリングされたインデックスの更新は「非常に高価な操作」であるため、データベースの仕組みに関する基本的な誤った情報を取り巻く都市の伝説です。正しいステートメントは、「クラスタ化されたキーに影響を与えるクラスタ化されたインデックスの更新は、すべての非クラスタ化インデックスを更新する必要があります」です。

+0

RDBを取り巻くように、都市の伝説がたくさんあることは本当に残念です。私は数週間で私はSQLを書いていた彼らの少数を押しつぶしました。私がIDを更新しない限り、(潜在的に)非常に高価な操作がクラスタ化されたデータに発生することはないと私は安全に仮定してもよいでしょうか? – Kivin

+2

はい、そうです。 – BradC

+5

IDを更新するには、* all *の他のインデックスに更新が必要です。索引の一部である他の列を更新するには、それらの索引の更新が必要です。索引の一部ではない列(キーまたは列を含む)は、追加の更新を引き起こしません。 など。 Flagsにインデックスがある場合、そのインデックスを維持するためのアップデートが追加アップデートされます。証拠が悪いことを指摘しない限り、私は更新について心配しません。ほとんどの場合、最適化されていない読み取り(スキャン)が問題です。ところで、TOP(1)は何ですか? IDはPKですね。 –

10

クラスタ化インデックス物理的なテーブルですので、あなたがに任意の行を更新するたびに、あなたはクラスタ化を更新している更新インデックス。クラスタ化インデックスとヒープ:

this MSDN article

+0

プライマリキーに影響を与える場合にのみ、クラスタ化インデックス更新を実行する必要があります。 しかし、私はあなたのポイントをキャッチします。 私は、クラスタ化されたインデックスの更新が危険なものだと思うと、洗脳されたと思います。 – Kivin

+1

これを回避する方法はありますか? – Serge

関連する問題