22

我有很多带有外键的表,有些有索引,而有些则没有。所有外键都以名为FK_<name of the foreign key>的索引命名IX_<name of the foreign key>

考虑到外键的列基数,是否有一些好的做法来创建(或不)索引?这可以编写为 T-SQL 命令吗?

4

2 回答 2

46

不管它们是通过 T-SQL 脚本还是通过设计器创建的。您的问题有点模棱两可,所以我不确定您是否还问是否可以索引所有外键。但是,如果您这样做,则应在查询中经常引用的列上创建索引,并且您可以执行以下操作来提高性能:

  • 运行数据库调整向导,它将提供改进摘要并推荐索引。

  • 索引所有外键并运行执行计划(查看查询执行得更快还是更慢)。

要通过以下方式创建索引T-SQL

CREATE INDEX IX_INDEX_NAME
ON Table (FieldName); 

要获取所有外键的列表:

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

要生成跨所有外键应用索引的脚本,您可以这样做:

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

于 2012-05-24T10:20:44.350 回答
1

大家辛苦了,很有帮助。

添加包含表模式的增强功能。如果您愿意,也可以排除 FK 名称(我倾向于不在小表上添加索引)

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
      ''
)
于 2017-12-06T13:51:10.690 回答