你可以这样做:
SELECT *
FROM Othertable t1
INNER JOIN #temp321 t2 ON t1.Field1 = t2.field1
AND t1.Field2 = t2.field2
AND t1.Field3 = t2.field3;
更新:这是我能做的:
JOIN
这两个表动态而不是WHERE
子句:
DECLARE @DynamicJOINCondition AS NVARCHAR(MAX);
DECLARE @query AS NVARCHAR(MAX);
;WITH cte
AS
(
SELECT t1.COLUMN_NAME 'T1', t2.COLUMN_NAME 'T2'
FROM
(
SELECT
ordinal_position ,
column_name
FROM information_schema.columns
WHERE table_name LIKE '#temp321%'
) t1
INNER JOIN
(
SELECT
ordinal_position ,
column_name
FROM information_schema.columns
WHERE table_name = 'othertable'
) t2 ON t1.ORDINAL_POSITION = t2.ORDINAL_POSITION
)
SELECT @DynamicJOINCondition = STUFF((SELECT distinct ' AND ' +
' t1.' + T1 + ' = ' + 't2.' + T2
FROM cte
FOR XML PATH(''), TYPE
).value('.', 'NVARCHAR(MAX)'), 4,1,'');
-- Remove the first AND
SELECT @DynamicJOINCondition = RIGHT(@DynamicJOINCondition,
LEN(@DynamicJOINCondition) - 4);
SET @query = 'SELECT COUNT(*) ' +
' FROM #temp321 t1 INNER JOIN Othertable t2 ON ' +
@DynamicJOINCondition;
EXECUTE(@query);
这是如何工作的?
首先,我JOIN
通过从临时表中获取列名列表和从另一个表中获取列名的另一个列表来动态生成条件。请注意它。我使用了 columns ORDINAL_POSITION
's,它是存储在表中的元数据,information_schema.columns
用于数据库中的每一列,来比较两个表中的列名列表。例如,具有普通位置 1 的列将与第二个表中具有普通位置 1 的列名连接,依此类推。因此,您必须注意临时表列的位置,以便以与第二个表的其他列列表相同的顺序列出的列。
更新2:
动态生成WHERE
子句:
如果您想WHERE
动态生成子句而不是 using JOIN
,在这种情况下将需要更多工作。像这样:
DECLARE @DynamicWHERECondition AS NVARCHAR(MAX);
DECLARE @query AS NVARCHAR(MAX);
;WITH cte
AS
(
SELECT t1.COLUMN_NAME 'T1', t2.COLUMN_NAME 'T2'
FROM
(
SELECT
ordinal_position,
column_name
FROM information_schema.columns
WHERE table_name LIKE '#temp321%'
) t1
INNER JOIN
(
SELECT
ordinal_position,
column_name
FROM information_schema.columns
WHERE table_name = 'othertable'
) t2 ON t1.ORDINAL_POSITION = t2.ORDINAL_POSITION
), cte2
AS
(
SELECT t2, fieldvalue
FROM cte t1
INNER JOIN
(
SELECT FieldName, fieldvalue
FROM
(
SELECT field1, field2, field3, field4
FROM #temp321
) p
UNPIVOT
(
fieldvalue FOR FieldName IN (field1, field2, field3, field4)
) AS u
) t2 ON t1.T2 = t2.FieldName
)
SELECT @DynamicWHERECondition = STUFF((SELECT distinct ' AND ' +
T2 + ' = ' + '''' + fieldvalue + ''''
FROM cte2
FOR XML PATH(''), TYPE
).value('.', 'NVARCHAR(MAX)'), 4,1,'');
SELECT @DynamicWHERECondition = RIGHT(@DynamicWHERECondition, LEN(@DynamicWHERECondition) - 4);
SET @query = 'SELECT COUNT(*) ' +
' FROM Othertable t2 WHERE ' + @DynamicWHERECondition;
EXECUTE(@query);
这是如何工作的?
由于临时表仅包含一行,其值将用于形成动态创建的WHERE
子句,因此我UNPIVOT
将这一行编辑为两列:fieldname: field1, field2, ...
和fieldvalue: value1, value2, ...
。
后来,我将这个未透视的列与我在第一个查询中使用的两个表连接起来:
SELECT
ordinal_position,
column_name
FROM information_schema.columns
WHERE table_name LIKE '#temp321%';
和:
SELECT
ordinal_position,
column_name
FROM information_schema.columns
WHERE table_name = 'othertable';
连接条件与第一种情况的条件相同,由两个表中列的序号位置决定。
动态生成WHERE
子句,动态生成UNPIVOT
临时表的值:
但是以前的方法有一个很大的问题。You need to unpivot table temp 的选择如下所示:
SELECT @cols = STUFF((SELECT DISTINCT ',' + QUOTENAME(column_name)
FROM information_schema.columns
WHERE table_name LIKE '#temp321%'
FOR XML PATH(''), TYPE
).value('.', 'NVARCHAR(MAX)'), 1, 1, '');
SET @dynamicunpivotquery = ' SELECT FieldName, fieldvalue ' +
' FROM ' +
' ( SELECT * FROM #temp321 ' +
' ) p ' +
' UNPIVOT ' +
' ( ' +
' fieldvalue FOR FieldName IN (' + @cols + ' ) ' +
' ) AS u ';
但是,为了稍后在我们的查询中使用动态未透视表,您必须创建一个临时表:
DECLARE @unpivotedTable TABLE(FieldName varchar(50), fieldvalue VARCHAR(50));
INSERT INTO @unpivotedTable
exec(@dynamicunpivotquery);
这样您就可以像这样使用它:
SELECT t2, fieldvalue
FROM cte t1
INNER JOIN @unpivotedTable t2 ON t1.T2 = t2.FieldName
这是带有动态反透视的更新后的 sql:
DECLARE @DynamicWHERECondition AS NVARCHAR(MAX);
DECLARE @cols AS NVARCHAR(MAX);
DECLARE @dynamicunpivotquery AS NVARCHAR(MAX);
DECLARE @query AS NVARCHAR(MAX);
DECLARE @unpivotedTable TABLE(FieldName varchar(50), fieldvalue VARCHAR(50));
SELECT @cols = STUFF((SELECT DISTINCT ',' + QUOTENAME(column_name)
FROM information_schema.columns
WHERE table_name LIKE '#temp321%'
FOR XML PATH(''), TYPE
).value('.', 'NVARCHAR(MAX)'), 1, 1, '');
SET @dynamicunpivotquery = ' SELECT FieldName, fieldvalue ' +
' FROM ' +
' ( SELECT * FROM #temp321 ' +
' ) p ' +
' UNPIVOT ' +
' ( ' +
' fieldvalue FOR FieldName IN (' + @cols + ' ) ' +
' ) AS u ';
INSERT INTO @unpivotedTable
exec(@dynamicunpivotquery);
;WITH cte
AS
(
SELECT t1.COLUMN_NAME 'T1', t2.COLUMN_NAME 'T2'
FROM
(
SELECT
ordinal_position,
column_name
FROM information_schema.columns
WHERE table_name LIKE '#temp321%'
) t1
INNER JOIN
(
SELECT
ordinal_position,
column_name
FROM information_schema.columns
WHERE table_name = 'othertable'
) t2 ON t1.ORDINAL_POSITION = t2.ORDINAL_POSITION
), cte2
AS
(
SELECT t2, fieldvalue
FROM cte t1
INNER JOIN @unpivotedTable t2 ON t1.T2 = t2.FieldName
)
SELECT @DynamicWHERECondition = STUFF((SELECT distinct ' AND ' +
T2 + ' = ' + '''' + fieldvalue + ''''
FROM cte2
FOR XML PATH(''), TYPE
).value('.', 'NVARCHAR(MAX)'), 4,1,'');
SELECT @DynamicWHERECondition = RIGHT(@DynamicWHERECondition,
LEN(@DynamicWHERECondition) - 4);
SET @query = 'SELECT COUNT(*) ' +
' FROM Othertable t2 WHERE ' + @DynamicWHERECondition;
EXECUTE(@query);