SELECT WHERE(列名是另一个查询的结果)

SELECT WHERE (column name is a result of another query)

我有两个表;

dbo.Users:

user_id user_name   gender   has_phone
--------------------------------------
1       admin       Male     true
2       UserA       Male     false
3       UserB       Female   true

dbo.Filterby:

id  name        filterid    filtervalue 
---------------------------------------
1   All         NULL        -1              
2   Males       gender      Male            
3   Females     gender      Female  
4   Phone       has_phone   true
5   NoPhone     has_phone   false

我需要 select 所有患者基于 filterby 的查询结果,所以例如我想要所有男性 returned:

SELECT 
    [user_id], [user_name] 
FROM 
    dbo.Users
WHERE 
    (SELECT filterid FROM dbo.Filterby WHERE id = 2) = (SELECT filtervalue FROM dbo.Filterby WHERE id = 2)

这应该更通用,所以我可以传入任何 Filterby.id 并且它会 return 正确的结果。但基本上,我真的只需要知道如何 select 使用另一个查询的结果作为列标识符。

我该怎么做?

谢谢。

根据我的经验,使用动态 SQL 将是执行此操作的最简单方法。看看下面的例子。基本上我认为你会想使用一个变量然后一些动态的 SQL.

来拆分它
DECLARE @Table_Name VARCHAR(1000) /*Would actually be an input parameter in  
our SP.*/

DECLARE @Statement VARCHAR(1000) /*Declaration of our SQL statement to 

execute.*/

SET @Table_Name = 'ErrorLog' /*The value for our input parameter*/

SET @Statement = 'SELECT * FROM ' + '[dbo].[' + @Table_Name + ']'; 

/*Dynamically creating the SQL statement with our table_name variable.*/

EXEC (@Statement); /*We execute the @statement to get our results.*/

上面的代码接受一个声明的变量,然后基于它执行一条语句。根据您的需要,您也可以使用变量。您也可以考虑在传递过滤值的存储过程中执行此操作。

declare @a nvarchar(30)

declare @table table (a nvarchar(30))

insert into @table values('select ''''''a''''''')

select @a=a from @table

exec(@a)

在第四行你存储 --> SELECT 'a' 到变量@a 在第五行你正在执行@a

在这里,您将 table 中的数据分配给某个变量并使用 exec() 命令执行该数据。


如果对您有帮助,请标记为答案或投票

您可以使用 CROSS JOIN

SELECT 
    user_id, user_name, gender, has_phone 
FROM (
    SELECT 
        u.user_id,u.user_name, u.gender,u.has_phone, 
        CASE ISNULL(f.filterid,'')
            WHEN '' THEN '-1'
            WHEN 'gender' THEN u.gender
            WHEN 'has_phone' THEN u.has_phone
        END AS val,
        f.filtervalue
    FROM users AS u
        CROSS JOIN Filterby AS f
    WHERE f.id=4  -- here id of filter
) AS m
WHERE
    val=filtervalue 

如果您需要使用两个或多个字段进行过滤,例如此过滤 table

id  name        filterid    filtervalue 
---------------------------------------
1   All         NULL        -1              
2   Males       gender      Male            
3   Females     gender      Female  
4   PhoneMales  has_phone   true
4   PhoneMales  gender      Male
5   NoPhone     has_phone   false

然后你可以使用魔法版本的查询

SELECT 
    m2.user_id, u2.user_name, u2.gender, u2.has_phone
FROM (
    SELECT user_id
    FROM (  
        SELECT
            u.user_id, 
            CASE ISNULL(f.filterid,'')
                WHEN '' THEN '-1'
                WHEN 'gender' THEN u.gender
                WHEN 'has_phone' THEN u.has_phone
            END AS val,
            f.filtervalue
        FROM users AS u
            CROSS JOIN Filterby AS f
        WHERE f.id=4  -- here id of filter
    ) AS m
    WHERE val=filtervalue 
    GROUP BY user_id
    HAVING COUNT(*)=(
        SELECT COUNT(*) FROM Filterby WHERE id=4 -- here must be the same filter id as above 
    )
) AS m2 
    INNER JOIN users AS u2
      ON m2.user_id=u2.user_id