SELECT field1 as "@q1_12"
FROM table1
FOR XML PATH ('qt'),TYPE
我需要在xml中调整此查询的结果,但字段的别名“ @ q1_12”应根据不同和复杂的条件而更改。
因此,是否可以将此属性的名称放入变量中并在查询中使用它(如某种动态sql) 有技巧或解决方法吗?
SELECT field1 as @attributename <-- this is a variable
FROM table1
FOR XML PATH ('qt'),TYPE
我知道,这里的字符“ @”令人困惑,它具有不同的含义,即被视为变量还是被视为文字(在此示例中,“ XML FOR”命令将使用该字段将字段的值放入属性中而不是元素)
此外,此查询用作子查询,因此使用CASE / IF非常困难,有什么主意吗?
答案 0 :(得分:2)
您的问题清楚地表明,您了解动态SQL,并获得了一些有关REPLACE()
的提示,可以在字符串级别解决此问题。
但是可能有一种方法,尤其是在可能的名称都已知并且列表不大的情况下:
DECLARE @mockupTable TABLE(ID INT IDENTITY,SomeValue VARCHAR(100));
INSERT INTO @mockupTable VALUES('Row 1'),('Row 2');
-如您所知,使用变量列别名是不可能的 ...
-您可以使用动态语句,但这会涉及一些主要缺点...(无特殊要求,难以进行输出...)
-但是您可以尝试一下
-为了模拟您的复杂条件,我只检查一个值(但是您会得到ghist):
DECLARE @SomeCondition INT=2;
SELECT CASE WHEN @SomeCondition=1 THEN SomeValue END AS [@q1_01]
,CASE WHEN @SomeCondition=2 THEN SomeValue END AS [@q1_02]
,CASE WHEN @SomeCondition=3 THEN SomeValue END AS [@q1_03]
--add all possible attribute names here...
FROM @mockupTable t
FOR XML PATH('qt'),TYPE;
背后的魔力:如果未明确指定(请参阅ELEMENTS XSINIL
,则使用FOR XML PATH()
创建的XML将忽略NULL值。
您可以声明所有可能的列名,如果不满足条件,则将全部省略。
这是相反的方法:
DECLARE @KeepThis VARCHAR(100)='q1_02';
SELECT
(
SELECT SomeValue AS [@q1_01]
,SomeValue AS [@q1_02]
,SomeValue AS [@q1_03]
FROM @mockupTable t
FOR XML PATH('qt'),TYPE
).query('for $qt in /qt
return
<qt>
{
for $a in $qt/@*[local-name(.)=sql:variable("@KeepThis")]
return $a
}
</qt>');
将以所有属性 by-by-side 来创建XML,而XQuery将仅返回我们要保留的属性。
答案 1 :(得分:0)
唯一的方法是使用动态SQL。您不能使用变量来替换对象,别名等的值。因此,您需要安全将其注入到语句中:
DECLARE @attributename sysname = N'@q1_12';
DECLARE @SQL nvarchar(MAX);
SET @SQL = N'SELECT field1 AS ' + QUOTENAME(@attributename) + NCHAR(13) + NCHAR(10) +
N'FROM table1' + NCHAR(13) + NCHAR(10) +
N'FOR XML PATH ('qt'),TYPE;';
EXEC sp_executesql @SQL;