查询表中每列的填充行数(SQL Server)

the*_*uth 3 sql t-sql sql-server

我正在尝试获取表中每列的非空值的计数。我研究了以下先前提出的SO问题,但没有找到满意的答案:

查询以列出数据库中每个表中的记录数

从表SQL Server中的每个列获取每个值的计数

SQL Server计算表的每一列中不同值的数量

我编写了以下代码,以尝试为我的表构建一个数据字典,以包括列的名称,每列中填充的行数,数据类型,长度以及它是否为主键:

SELECT 
    c.name 'Column Name',
    p.rows 'Row_Count',
    t.Name 'Data type',
    c.max_length 'Max Length',
    ISNULL(i.is_primary_key, 0) 'Primary Key'
FROM    
    sys.columns c
INNER JOIN 
    sys.types t ON c.user_type_id = t.user_type_id
LEFT OUTER JOIN 
    sys.index_columns ic ON ic.object_id = c.object_id AND ic.column_id = c.column_id
LEFT OUTER JOIN 
    sys.indexes i ON ic.object_id = i.object_id AND ic.index_id = i.index_id
LEFT OUTER JOIN
sys.partitions p ON p.OBJECT_ID = i.OBJECT_ID and i.index_id = p.index_id
WHERE
    c.object_id = OBJECT_ID('my_table')
Run Code Online (Sandbox Code Playgroud)

但是,Row_Count列返回所有Null。

我的预期结果如下所示:

Column_Name Row_Count Data_Type Max_Length Primary_Key
A              10       varchar   50            0
B              10       varchar   50            0
C              7        float     50            0
D              3        float     50            0
E              10       varchar   50            0
Run Code Online (Sandbox Code Playgroud)

Joh*_*tti 5

这是一个不使用动态SQL的选项。

全面披露后,我怀疑DS的表现会更好。也就是说,这几乎可以在任何表,视图或查询上使用。我master..spt_values用作示范

Select ColumnName      = Item
      ,B.column_ordinal
      ,Row_Count       = sum(1)
      ,B.system_type_name
      ,B.max_length
      ,Distinct_Values = count(DISTINCT Value)
 From  (
        Select C.*
         From  master..spt_values A
         Cross Apply ( values (cast((Select A.* for XML RAW) as xml))) B(XMLData)
         Cross Apply (
                        Select Item  = replace(xAttr.value('local-name(.)', 'varchar(100)'),'_x0020_',' ')
                              ,Value = xAttr.value('.','varchar(max)')
                         From  XMLData.nodes('//@*') xNode(xAttr)
                     ) C
       ) A
 Left Join  (
        Select * from sys.dm_exec_describe_first_result_set('Select * from master..spt_values',null,null )  
       ) B on A.Item=B.name
 Group By A.Item
         ,B.system_type_name
         ,B.max_length
         ,B.column_ordinal 
 Order By B.column_ordinal 
Run Code Online (Sandbox Code Playgroud)

退货

在此处输入图片说明

编辑

正如Larnu提到的那样,这将导致(var)binary和image失败。同样,这在大型桌子上效果不佳。我仅在发现阶段使用过这种方法。