复杂的SQL查询 - 查找匹配多个不同外键的项目
所以想象一下你有一张
Products (ID int, Name nvarchar(200))
和另外两张桌子,ProductsCategories (ProductID int, CategoryID int)
和InvoiceProducts (InvoiceID int, ProductID int)
。
我需要编写一个查询来生成一组与给定的发票ID和类别ID匹配的产品,这样产品列表就可以匹配所有指定的类别和所有指定的发票,而不会回退到动态SQL。想象一下,我需要找到1类和2类以及发票3和4中的产品列表。
首先,我编写了一个存储过程,它接受类别ID和发票ID作为字符串,并将它们解析为表:
CREATE PROCEDURE dbo.SearchProducts (@categories varchar(max), @invoices varchar(max))
AS BEGIN
with catids as (select cast([value] as int) from dbo.split(@categories, ' ')),
invoiceids as (select cast([value] as int) from dbo.split(@invoices, ' '))
select * from products --- insert awesomeness here
END
我提出的不同解决方案看起来很糟糕,而且表现更差。我发现的最好的事情是生成一个由所有条件的左连接组成的视图,但这似乎非常昂贵,并没有解决匹配指定的所有不同键的问题。
更新:这是我编写的一个示例查询,可以产生预期的结果。我错过了任何优化机会吗?像忍者的魔法独角兽矩阵操作一样?
with catids as (select distinct cast([value] as int) [value] from dbo.split(@categories, ' ')),
invoiceids as (select distinct cast([value] as int) [value] from dbo.split(@invoices, ' '))
select pc.ProductID from ProductsCategories pc (nolock)
inner join catids c on c.value = pc.CategoryID
group by pc.ProductID
having COUNT(*) = (select COUNT(*) from catids)
intersect
select ip.ProductID from InvoiceProducts ip (nolock)
inner join invoiceids i on i.value = ip.InvoiceID
group by ip.ProductID
having COUNT(*) = (select COUNT(*) from invoiceids)
没有找到相关结果
已邀请:
5 个回复
琶竞捆栓
和
都有唯一的索引:
或者,如果您的值以
字符串传递:
请注意,在
中,您可以将表值参数传递给存储过程。
雇砰
桑娠贯涤
搂腹时
这将为您提供一种在多个条件上执行AND的方法,并且应该表现良好。 这有什么意义吗?我最近用CTE做了一些非常酷的快速的东西,如果有必要可以详细说明。 删除了cte代码,因为它错了,并没有真正值得修复那里有更好的解决方案。
磐去裸猜饲