将字段联接回主表的自定义表

时间:2019-02-02 06:49:18

标签: sql sql-server

我/需要以下表,其存储表下面字段具有一个值,以满足资格。

基本上Client.Field1必须包含的值为1,Client.Field2 2的值等

有人知道我如何在Client表中所有值都匹配时返回True,或者如果Client表中的值不匹配时返回False,并且足够灵活,如果添加了额外的字段,它将被提取?

CREATE TABLE [CustomField](
    [CustomFieldID] [smallint] IDENTITY(1,1) NOT NULL,
    [FieldTable] [nvarchar](100) NOT NULL,
    [FieldName] [nvarchar](100) NOT NULL,
    [EligibilityValue] [tinyint] NULL,
 CONSTRAINT [PK_CustomField] PRIMARY KEY CLUSTERED 
(
    [CustomFieldID] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
)
GO
INSERT [CustomField] ([CustomFieldID], [FieldTable], [FieldName], [EligibilityValue]) VALUES (119, N'Client', N'Field1', 1)
GO
INSERT [CustomField] ([CustomFieldID], [FieldTable], [FieldName], [EligibilityValue]) VALUES (120, N'Client', N'Field2', 2)
GO
INSERT [CustomField] ([CustomFieldID], [FieldTable], [FieldName], [EligibilityValue]) VALUES (130, N'Client', N'Field3', 1)
GO
INSERT [CustomField] ([CustomFieldID], [FieldTable], [FieldName], [EligibilityValue]) VALUES (141, N'Client', N'Field4', 2)
GO

CREATE TABLE Client
(
    ClientID int,
    Field1 int,
    Field2 int,
    Field3 int,
    Field4 int
)

--this would return True when the comparison is done
insert into Client
(
    ClientID,
    Field1,
    Field2,
    Field3,
    Field4
)
values
(
    100,
    1,
    2,
    1,
    2
)

--this would return False when the comparison is done
insert into Client
(
    ClientID,
    Field1,
    Field2,
    Field3,
    Field4
)
values
(
    101,
    1,
    2,
    2,
    2
)

2 个答案:

答案 0 :(得分:1)

您首先需要多行转换表customfield以单行,这样就可以轻松地将其与Client表进行比对。

您可以像使用CTEPIVOT一样编写查询。

;WITH cte 
     AS (SELECT [field1], 
                [field2], 
                [field3], 
                [field4] 
         FROM   (SELECT fieldtable, 
                        fieldname, 
                        eligibilityvalue 
                 FROM   customfield) AS SourceTable 
                PIVOT ( Max(eligibilityvalue) 
                      FOR fieldname IN ([Field1], 
                                        [Field2], 
                                        [Field3], 
                                        [Field4]) ) AS pivottable) 
SELECT c.*, 
       COALESCE(O.found, 'Not Found') AS Found 
FROM   client C 
       OUTER APPLY (SELECT 'Found' Found 
                    FROM   cte CT 
                    WHERE  CT.field1 = c.field1 
                           AND CT.field2 = c.field2 
                           AND CT.field3 = c.field3 
                           AND CT.field4 = c.field4) O 

输出

ClientID    Field1  Field2  Field3  Field4  Found
100          1       2       1        2     Found
101          1       2       2        2     Not Found

Online Demo

注意:代替使用OUTER APPLY,您还可以使用子查询。

编辑

要使其动态化,您需要使用PIVOT编写动态查询,如下所示。

DECLARE @cols AS NVARCHAR(max) = Stuff((SELECT DISTINCT ', ' + Quotename([FieldName]) 
         FROM   CustomField
         FOR xml path(''), type).value('.', 'NVARCHAR(MAX)'), 1, 1, ''); 

DECLARE @sqltext VARCHAR(MAX)

SELECT @sqltext = ISNULL(@sqltext,'')  + 'CT.' + C.[FieldName]  + ' = ' + 'C.' + C.[FieldName] + ' AND '  +  CHAR(10)
  FROM CustomField c
  --Append Ending Condition
SET @sqltext = @sqltext + ' 1=1'



DECLARE @query AS NVARCHAR(max) ='
;WITH CTE AS
(
    SELECT ' + @cols + '    

     FROM  
    (SELECT FieldTable, FieldName, EligibilityValue   
        FROM CustomField) AS SourceTable  
    PIVOT  
    (  
    max(EligibilityValue)  
    FOR FieldName IN (' + @cols + ')  
    ) AS PivotTable  

)
SELECT c.*, COALESCE(O.Found,''Not Found'') as Found FROM Client C
OUTER APPLY
(
    SELECT ''Found'' Found FROM CTE CT where ' +  @sqltext + '
) O'

EXEC (@query)

Online Demo for Dynamic Query

答案 1 :(得分:0)

您可以只使用EXCEPT。例如:

IF EXISTS
(
SELECT *
FROM Client
WHERE ClientID = 100
EXCEPT
SELECT *
FROM Client
WHERE ClientID = 101
)
BEGIN;
    SELECT 'not equal'
END;