zoukankan      html  css  js  c++  java
  • sqlserver用于统计表索引情况

    /*eg:
    
    --调用该过程实例
    --1 创建临时表
    IF OBJECT_ID('tempdb..#index_sql_text') IS NOT NULL
        DROP TABLE #index_sql_text
    CREATE TABLE #index_sql_text(
        tablename varchar(700),
        index_name VARCHAR(200),
        index_description VARCHAR(200),
        index_keys VARCHAR(200),
        create_sql_test VARCHAR(500),
        drop_sql_test VARCHAR(500)
        )
    
    --2 执行过程向临时表写入数据
    EXEC pro_index_sql_text 'ED_RetailPriceIndex','PK_ED_RetailPriceIndex'
    
    --3 使用临时表数据
    SELECT * FROM #index_sql_text
    
    */
    
    IF EXISTS (SELECT TOP 1 1 FROM sys.objects where type = 'P' AND name = 'pro_index_sql_text')
        DROP PROCEDURE pro_index_sql_text
    GO
    
    CREATE PROCEDURE pro_index_sql_text
        @objname nvarchar(776),        --表名:该变量不能为空,所以不默认指定
        @indexname nvarchar(200) = NULL   --索引名:当指定索引时返回该索引数据,当没有指定值时默认返回表的所有索引
    AS
    
    /*
        最后修改日期:2016-12-08
        说明:给定表名,返回对应表的索引,主键,唯一约束键的删除及新建脚本
        参数:@objname-表名,必须指定,不能包含架构名如 dbo.table(有问题),table(正确)
              @indexname-索引名:当指定索引时返回该索引数据,当没有指定值时默认返回表的所有索引
    
        --declare @objname varchar(776)
        --select @objname = 'TEST_TABLE'
    */
    
    --1 判断过程外面是否已经创建,创建临时表 #index_sql_text 存放最后结果
    IF OBJECT_ID('tempdb..#index_sql_text') IS NULL
    BEGIN
        CREATE TABLE #index_sql_text(
            tablename varchar(700),
            index_name VARCHAR(200),
            index_description VARCHAR(200),
            index_keys VARCHAR(200),
            create_sql_test VARCHAR(500),
            drop_sql_test VARCHAR(500)
            )
    END
    
    --2 声明变量并检查库表关系(借鉴系统过程 sp_helpindex)
    declare @objid int, -- the object id of the table
        @indid smallint, -- the index id of an index
        @groupid int, -- the filegroup id of an index
        @indname sysname,
        @groupname sysname,
        @status int,
        @keys nvarchar(2126), --Length (16*max_identifierLength)+(15*2)+(16*3)
        @dbname sysname,
        @ignore_dup_key bit,
        @is_unique bit,
        @is_hypothetical bit,
        @is_primary_key bit,
        @is_unique_key bit,
        @auto_created bit,
        @no_recompute bit
    
    --@dbname 赋值
    select @dbname = parsename(@objname,3)
    if @dbname is null
    select @dbname = db_name()
    
    -- Check to see the the table exists and initialize @objid.
    select @objid = object_id(@objname)
    if @objid is NULL
    begin
        raiserror(15009,-1,-1,@objname,@dbname)
        return
    end
    
    --3 声明游标(包括该表的索引情况)
    declare ms_crs_ind cursor local static for
    select
        i.index_id,
        i.data_space_id,
        i.name,
        i.ignore_dup_key,
        i.is_unique,
        i.is_hypothetical,
        i.is_primary_key,
        i.is_unique_constraint,
        s.auto_created,
        s.no_recompute
    from sys.indexes i
    join sys.stats s on i.object_id = s.object_id and i.index_id = s.stats_id
    where i.object_id = @objid     --限制对象名称
        and (i.name = @indexname OR @indexname IS NULL)    --限制索引名称
    
    --打开游标
    open ms_crs_ind
    
    --获取游标数据
    fetch ms_crs_ind into @indid, @groupid, @indname, @ignore_dup_key, @is_unique, @is_hypothetical,
    @is_primary_key, @is_unique_key, @auto_created, @no_recompute
    
    -- IF NO INDEX, QUIT
    if @@fetch_status < 0
    begin
        deallocate ms_crs_ind
        raiserror(15472,-1,-1,@objname) -- Object does not have any indexes.
        return
    end
    
    --4 新建存放基础数据临时表 #spindtab
    IF OBJECT_ID('tempdb..#spindtab') IS NOT NULL
        DROP TABLE #spindtab
    CREATE TABLE #spindtab
    (
        index_name sysname collate database_default NOT NULL,
        index_id int,
        ignore_dup_key bit,
        is_unique bit,
        is_hypothetical bit,
        is_primary_key bit,
        is_unique_key bit,
        auto_created bit,
        no_recompute bit,
        groupname sysname collate database_default NULL,
        index_keys nvarchar(2126) collate database_default NOT NULL -- see @keys above for length descr
    )
    
    -- Now check out each index, figure out its type and keys and
    -- save the info in a temporary table that we'll print out at the end.
    while @@fetch_status = 0
    begin
        -- First we'll figure out what the keys are.
        declare @i int, @thiskey nvarchar(131) -- 128+3
    
        /*
        返回索引信息及索引字段的升降序
        INDEXKEY_PROPERTY ( object_ID ,index_ID ,key_ID ,property )
        property 要返回其信息的属性的名称。
        IsDescending
        存储索引列的排序顺序。
        1 = 降序 0 = 升序
        */
        select @keys = index_col(@objname, @indid, 1), @i = 2
        if (indexkey_property(@objid, @indid, 1, 'isdescending') = 1)
        --select @keys = @keys + '(-)'
        select @keys = @keys + ' desc'
    
        select @thiskey = index_col(@objname, @indid, @i)
        if ((@thiskey is not null) and (indexkey_property(@objid, @indid, @i, 'isdescending') = 1))
        --select @thiskey = @thiskey + '(-)'
        select @thiskey = @thiskey + ' desc'
    
        while (@thiskey is not null )
        begin
            select @keys = @keys + ', ' + @thiskey, @i = @i + 1
            select @thiskey = index_col(@objname, @indid, @i)
            if ((@thiskey is not null) and (indexkey_property(@objid, @indid, @i, 'isdescending') = 1))
            --select @thiskey = @thiskey + '(-)'
            select @thiskey = @thiskey + ' desc'
        end
    
        select @groupname = null
        select @groupname = name from sys.data_spaces where data_space_id = @groupid
    
        -- INSERT ROW FOR INDEX
        insert into #spindtab values (@indname, @indid, @ignore_dup_key, @is_unique, @is_hypothetical,
            @is_primary_key, @is_unique_key, @auto_created, @no_recompute, @groupname, @keys)
    
        -- Next index 获取游标下一条数据
        fetch ms_crs_ind into @indid, @groupid, @indname, @ignore_dup_key, @is_unique, @is_hypothetical,
            @is_primary_key, @is_unique_key, @auto_created, @no_recompute
    end
    deallocate ms_crs_ind
    
    --5 结果集拼接并写入临时表
    insert into #index_sql_text
    select
        @objname,
        'index_name' = index_name,
        'index_description' = convert(varchar(210), --bits 16 off, 1, 2, 16777216 on, located on group
                                case when index_id = 1 then 'clustered' else 'nonclustered' end
                                    + case when ignore_dup_key <>0 then ', ignore duplicate keys' else '' end
                                    + case when is_unique <>0 then ', unique' else '' end
                                    + case when is_hypothetical <>0 then ', hypothetical' else '' end
                                    + case when is_primary_key <>0 then ', primary key' else '' end
                                    + case when is_unique_key <>0 then ', unique key' else '' end
                                    + case when auto_created <>0 then ', auto create' else '' end
                                    + case when no_recompute <>0 then ', stats no recompute' else '' end
                                    + ' located on ' + groupname),
        'index_keys' = index_keys,
        'create_sql_test' = CASE WHEN is_primary_key  = 1 THEN 'ALTER TABLE ' + @objname+ ' ADD CONSTRAINT ' + index_name + ' PRIMARY KEY '
                                        +CASE WHEN index_id =1 THEN 'CLUSTERED ' ELSE 'NONCLUSTERED ' END
                                        +'('+index_keys+');'
                                  WHEN is_primary_key  = 0 AND is_unique_key = 1 THEN 'ALTER TABLE ' + @objname+ ' ADD CONSTRAINT ' + index_name
                                        +CASE WHEN is_unique =0 THEN '' ELSE ' UNIQUE ' END
                                        +CASE WHEN index_id =1 THEN 'CLUSTERED ' ELSE 'NONCLUSTERED ' END
                                        +'('+index_keys+');'
                                  WHEN is_primary_key  = 0 AND is_unique_key = 0 THEN 'CREATE ' +
                                        CASE WHEN is_unique =0 THEN '' ELSE 'UNIQUE ' END +
                                        CASE WHEN index_id =1 THEN 'CLUSTERED ' ELSE 'NONCLUSTERED ' END + 'INDEX '+index_name+
                                        ' on ' + @objname+'('+index_keys+');'
                                END,
        'drop_sql_test' = CASE WHEN is_primary_key  = 1 THEN 'ALTER TABLE ' + @objname+ ' DROP CONSTRAINT ' + index_name+';'
                              WHEN is_primary_key  = 0 AND is_unique_key = 1 THEN 'ALTER TABLE ' + @objname
                                    + ' DROP CONSTRAINT ' + index_name+';'
                              WHEN is_primary_key  = 0 AND is_unique_key = 0 THEN 'DROP INDEX ' + @objname
                                    +'.'+  index_name+';'
                          END
    from #spindtab
    order by index_name
    
    /* 
    --调试代码是方便查看,用于调度时不需要该语句
    SELECT * FROM #index_sql_text
    */
  • 相关阅读:
    npm 安装卸载模块 & ionic插件安装与卸载
    Vue中v-model解析、sync修饰符解析
    Vue props用法详解
    vue页面跳转
    Swift 4 中的泛型
    Swift枚举的全用法
    蓝牙 BLE 三种 UUID 格式转换
    SVG图案
    SVG渐变
    SVG坐标系统及图形变换
  • 原文地址:https://www.cnblogs.com/xiaozhi1236/p/5618072.html
Copyright © 2011-2022 走看看