6

我可以这样声明一个表变量:

DECLARE @tv_source TABLE(c1 int, 
providerName varchar(50),
providerSMS varchar(50))

如果我随后执行以下命令,我会看到类似于以下内容的表名:“#468862B0”

select top 1 * from tempdb.sys.tables where type = 'U' order by create_date desc
select TOP 1 name,* from tempdb.sys.sysobjects ORDER BY CRDATE desc

如果我立即执行:

select TOP 3 * 
from tempdb.sys.columns 
where object_id in (select TOP 1 object_id from tempdb.sys.tables ORDER BY Create_date desc)

我看到了我在上面为表变量声明的列。

我的问题是,有没有办法将这些列与我在“@tv_source”上方的表声明中声明的名称明确关联?

在普通表中,您会看到实际名称,但如上所述,表变量会变形为十六进制值(顺便说一句,它是 object_id 的十六进制值)。

4

2 回答 2

6

top(0)您可以使用outer apply从一行查询您的表变量,for xml path('')然后在 XML 中查询元素名称。

只要您的列名没有无效的 XML 元素名称,这将起作用。例如,列名可以不使用与号或空格。

declare @tv_source table
(
  c1 int, 
  providerName varchar(50),
  providerSMS varchar(50)
)

select TN.N.value('local-name(.)', 'sysname') as ColumnName
from 
  (
  select TV.*
  from (select 1) as D(N)
    outer apply (
                select top(0) *
                from @tv_source
                ) as TV
  for xml path(''), elements xsinil, type
  ) as TX(X)
cross apply TX.X.nodes('*') as TN(N)

另一种选择是xmlschema使用for xml auto. 此解决方案确实可以处理无效的 XML 字符,但它们会被转义,因此如果您有一个带有空格的列名,[provider Name]结果将是provider_x0020_Name.
您需要将生成的 XML 存储到一个变量中,并在该变量中查询您想要的信息。

declare @XML xml;

set @XML = 
  (
  select top(0) *
  from @tv_source
  for xml auto, xmlschema, type
  );

with xmlnamespaces('http://www.w3.org/2001/XMLSchema' as xsd)
select T.X.value('@name', 'sysname')
from @XML.nodes('//xsd:attribute') as T(X);

由 所创建的 XMLxmlschema包含更多可能感兴趣的信息。您也可以检索表变量名称和数据类型。

<xsd:schema xmlns:schema="urn:schemas-microsoft-com:sql:SqlRowSet12" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:sqltypes="http://schemas.microsoft.com/sqlserver/2004/sqltypes" targetNamespace="urn:schemas-microsoft-com:sql:SqlRowSet12" elementFormDefault="qualified">
  <xsd:import namespace="http://schemas.microsoft.com/sqlserver/2004/sqltypes" schemaLocation="http://schemas.microsoft.com/sqlserver/2004/sqltypes/sqltypes.xsd" />
  <xsd:element name="_x0040_tv_source">
    <xsd:complexType>
      <xsd:attribute name="c1" type="sqltypes:int" />
      <xsd:attribute name="providerName">
        <xsd:simpleType>
          <xsd:restriction base="sqltypes:varchar" sqltypes:localeId="1035" sqltypes:sqlCompareOptions="IgnoreCase IgnoreKanaType IgnoreWidth">
            <xsd:maxLength value="50" />
          </xsd:restriction>
        </xsd:simpleType>
      </xsd:attribute>
      <xsd:attribute name="providerSMS">
        <xsd:simpleType>
          <xsd:restriction base="sqltypes:varchar" sqltypes:localeId="1035" sqltypes:sqlCompareOptions="IgnoreCase IgnoreKanaType IgnoreWidth">
            <xsd:maxLength value="50" />
          </xsd:restriction>
        </xsd:simpleType>
      </xsd:attribute>
    </xsd:complexType>
  </xsd:element>
</xsd:schema>
于 2013-01-17T06:36:53.503 回答
1

我从你的评论中看到,这个练习是为了学习,所以你没有特定的用例或需求。也就是说,从表变量变量中获取详细列元数据的另一种方法是使用 sp_describe_first_result_set。

EXEC sp_describe_first_result_set @tsql =  N'
declare @tableName table (ID bigint,
                            Column1 bigint,
                            Column2 datetime,
                            createdBy nvarchar(100),
                            dateAdded nvarchar(12),
                            Type nvarchar(10)
                            )
SELECT * FROM @tableName;';
于 2018-03-09T12:51:20.177 回答