在多行中使用“IN”?

she*_*key 3 sql-server-2008 sql-server

所以我得到了一个带有一大堆连接的查询,它返回一行,像这样(只是一个例子):

select t1.chickenId, t2.beefId, t3.fishId from Food f
join t1 on t1.id = f.id
join t2 on t2.id = f.id
join t3 on t3.id = f.id
where f = 'something' 
Run Code Online (Sandbox Code Playgroud)

结果是这样的,例如:

chickenId | beefId | fishId
5          58         14
Run Code Online (Sandbox Code Playgroud)

现在我不知道该怎么做的部分......使用上面的查询的原因是因为我想使用结果在另一个表中找到一些东西。

我有另一个名为“Extras”的表,我希望该表中的行具有来自上一个查询的任何列的 ID。因此,如果 id 5、58 或 14 在 Extras 表中,我想要这些行。

以下查询不正确,但我相信它可以用来演示我想要实现的目标:

select * from Extras where extra = 'Potatoes' and foodId in (select t1.chickenId, t2.beefId, t3.fishId from Food f
    join t1 on t1.id = f.id
    join t2 on t2.id = f.id
    join t3 on t3.id = f.id
    where f = 'something')
Run Code Online (Sandbox Code Playgroud)

知道我如何实现这一目标吗?我正在使用 Microsoft 的 SQL Server 2008

ype*_*eᵀᴹ 6

您的IN子查询有 3 列,因此无法与Extras.foodId.

您可以EXISTS改为使用并将IN条件移动到内部,使其成为相关子查询:

select e.* 
from Extras as e
where e.extra = 'Potatoes'
  and exists
      ( select *
        from Food as f
          join t1 on t1.id = f.id
          join t2 on t2.id = f.id
          join t3 on t3.id = f.id
        where f.f = 'something' 
          and e.foodId in (t1.chickenId, t2.beefId, t3.fishId)
      ) ;
Run Code Online (Sandbox Code Playgroud)

另一种可能性是保留IN您拥有的语法并将 3 列转换为一列(每行转换为 3 列)CROSS APPLY

select e.* 
from Extras as e 
where e.extra = 'Potatoes' 
  and e.foodId in 
      ( select v.foodId
        from Food as f
          join t1 on t1.id = f.id
          join t2 on t2.id = f.id
          join t3 on t3.id = f.id
          cross apply
            ( select t1.chickenId union
              select t2.beefId    union
              select t3.fishId
            ) as v (foodId) 
        where f.f = 'something' 
      ) ;
Run Code Online (Sandbox Code Playgroud)

如果您提供的第一个查询保证总是返回一行,您还可以使用没有任何子查询的简单连接:

select e.* 
from Food as f
  join t1 on t1.id = f.id
  join t2 on t2.id = f.id
  join t3 on t3.id = f.id
  join Extras as e 
    on e.foodId in (t1.chickenId, t2.beefId, t3.fishId)
where e.extra = 'Potatoes'
  and f.f = 'something' ;
Run Code Online (Sandbox Code Playgroud)