2012-05-24 35 views
15

Tôi có nhiều bảng có khóa ngoài và một số có chỉ mục trong khi một số khác thì không. Tất cả các khóa ngoại được đặt tên là FK_<name of the foreign key> với các chỉ mục có tên IX_<name of the foreign key>.máy chủ sql: tạo chỉ mục trên các khóa ngoài khi cần thiết

Có một số thực hành tốt, được đưa ra cho tính chính xác của khóa ngoại, để tạo ra (hoặc không) chỉ mục? Điều này có thể được viết thành các lệnh T-SQL không?

+0

Tôi nghĩ rằng bạn cần phải làm rõ câu hỏi của bạn, xem quan sát này trong câu trả lời của Darren: * "Câu hỏi của bạn là một chút mơ hồ , vì vậy tôi không chắc chắn liệu bạn có đang hỏi liệu có thể lập chỉ mục tất cả các khóa ngoại không. "* – Kev

Trả lời

32

Không quan trọng nếu chúng được tạo thông qua Tập lệnh T-SQL hoặc qua Trình thiết kế. Câu hỏi của bạn là một chút mơ hồ, vì vậy tôi không chắc chắn nếu bạn cũng yêu cầu nếu nó là okay để lập chỉ mục tất cả các phím nước ngoài. Tuy nhiên, nếu bạn đang có, chỉ cần được tạo ra trên các cột được tham chiếu thường xuyên trong các truy vấn và bạn có thể làm như sau để cải thiện hiệu suất:

  • Chạy thuật sĩ cơ sở dữ liệu điều chỉnh mà sẽ cung cấp một bản tóm tắt của những cải tiến và giới thiệu chỉ số .

  • Lập chỉ mục tất cả khóa ngoại và chạy kế hoạch thực hiện (Để xem liệu truy vấn có hoạt động nhanh hơn hay chậm hơn).

Để tạo một chỉ số qua T-SQL:

CREATE INDEX IX_INDEX_NAME 
ON Table (FieldName); 

Để có được một danh sách tất cả các phím nước ngoài:

SELECT f.name AS ForeignKey, 
OBJECT_NAME(f.parent_object_id) AS TableName, 
COL_NAME(fc.parent_object_id, fc.parent_column_id) AS ColumnName, 
OBJECT_NAME (f.referenced_object_id) AS ReferenceTableName, 
COL_NAME(fc.referenced_object_id, fc.referenced_column_id) AS ReferenceColumnName 
FROM sys.foreign_keys AS f 
INNER JOIN sys.foreign_key_columns AS fc 
ON f.OBJECT_ID = fc.constraint_object_id 

Để tạo ra một kịch bản áp dụng chỉ số trên tất cả các phím nước ngoài bạn có thể làm điều này:

SELECT 'CREATE INDEX [IX_' + f.name + '] ON ' + OBJECT_NAME(f.parent_object_id) + '(' + COL_NAME(fc.parent_object_id, fc.parent_column_id) + ')]' 
FROM sys.foreign_keys AS f 
INNER JOIN sys.foreign_key_columns AS fc 
ON f.OBJECT_ID = fc.constraint_object_id 

http://msdn.microsoft.com/en-us/library/ms188783.aspx

+0

Tôi đã làm rõ câu hỏi, tôi muốn thực hiện việc này bằng cách sử dụng tập lệnh T-SQL – psadac

+0

@psadac - Cập nhật bài đăng của tôi. –

+0

'Để tạo ra một kịch bản áp dụng các chỉ mục trên tất cả các phím nước ngoài' - Điều gì chỉ là các phím nước ngoài với một cardinality nhất định? –

0

Làm việc tuyệt vời mọi người, rất hữu ích.

Thêm tính năng nâng cao bao gồm lược đồ bảng. Bạn cũng có thể loại trừ tên FK nếu bạn thích (Tôi có xu hướng không để thêm chỉ số trên bảng nhỏ)

SELECT 
    * 
FROM 
(
    SELECT TOP 99 PERCENT 
      f.name AS ForeignKeyName 

     , s.name 
       + '.' 
       + OBJECT_NAME(f.parent_object_id) 
       + '.' 
       + COL_NAME(fc.parent_object_id, fc.parent_column_id) 
      ParentTable 

     , referencedSchema.name 
       + '.' 
       + OBJECT_NAME (f.referenced_object_id) 
       + '.' 
       + COL_NAME(fc.referenced_object_id, fc.referenced_column_id) 
      ReferencedTable 

     , 'CREATE INDEX [IX_' + f.name + ']' 
       + ' ON ' 
        + '[' + referencedSchema.name + ']' 
        + '.' 
        + '[' + OBJECT_NAME(f.parent_object_id) + ']' 
        + '(' 
         + COL_NAME(fc.parent_object_id, fc.parent_column_id) 
        + ')' 
      CreateIndexSql   

    FROM 
     sys.foreign_keys AS f 
     INNER JOIN sys.foreign_key_columns AS fc ON f.OBJECT_ID = fc.constraint_object_id 
     inner join sys.schemas s on f.schema_id = s.schema_id 

     inner join sys.tables referencedTable on f.referenced_object_id = referencedTable.object_id 
     inner join sys.schemas referencedSchema on referencedTable.schema_id = referencedSchema.schema_id 

    ORDER BY 
     2, 3, 1 
) a 
where a.ParentTable not in (
    -- Add any exclusions here so you can forget about them 
     '' 
) 
Các vấn đề liên quan