SQL返回表中前10个不同的结果,而不是所有结果中的前10个

SQL返回表中前10个不同的结果,而不是所有结果中的前10个,sql,sql-server,stored-procedures,Sql,Sql Server,Stored Procedures,我有一个简单的数据库,设置了3个表,一个中央产品存储库(product),一个供应商列表以及他们从该存储库中提供的产品(Supplier_product),一个商店列表以及他们从存储库中库存的产品(Site_product) 我需要一次返回分页10个独特的产品,以及由于加入而产生的任何其他供应商行和站点行。我得到了下面的查询,它返回10个产品,但它们显然不是唯一的,因为您可以在结果集中包含来自供应商1的产品1和来自供应商2的产品1 @Supplier\u Id、@Site\u Id和@Searc

我有一个简单的数据库,设置了3个表,一个中央产品存储库(product),一个供应商列表以及他们从该存储库中提供的产品(Supplier_product),一个商店列表以及他们从存储库中库存的产品(Site_product)

我需要一次返回分页10个独特的产品,以及由于加入而产生的任何其他供应商行和站点行。我得到了下面的查询,它返回10个产品,但它们显然不是唯一的,因为您可以在结果集中包含来自供应商1的产品1和来自供应商2的产品1

@Supplier\u Id、@Site\u Id和@Search\u术语用于筛选结果集

为了清楚起见,我不打算在结果集中返回10行,而是返回10个产品,以及它们的相关供应商/站点信息,作为重复的产品行

我希望这是有道理的

@Current_Page INT,
@Items_Per_Page INT = 10,
@Supplier_Id INT = NULL,
@Site_Id INT = NULL,
@Search_Term NVARCHAR(128) = NULL

SELECT P.Container_Noun, P.Open_Noun, P.Packaged, P.Product_Id, P.Product_Name, P.Quantity_Per_Package, P.Volume
SUP.Price, SUP.Supplier_Id, SUP.Supplier_Name,
SP.Site_Id, SP.Site_Name
FROM Product P
LEFT JOIN Supplier_Product SUP ON P.Product_Id = SUP.Product_Id
LEFT JOIN Site_Product SP ON P.Product_Id = SP.Product_Id
WHERE 
    (SUP.Supplier_Id = @Supplier_Id OR @Supplier_Id IS NULL) AND
    (SP.Site_Id = @Site_Id OR @Site_Id IS NULL) AND
    (P.Product_Name LIKE ('%' + @Search_Term + '%') OR @Search_Term IS NULL)
ORDER BY P.Product_Name ASC
OFFSET @Items_Per_Page *  (@Current_Page - 1) ROWS
FETCH NEXT @Items_Per_Page ROWS ONLY;

我真的希望这能起作用,因为我没有和您使用的表相同的表

如果你有任何错误,请告诉我,我会尽力帮助你

@Current_Page INT,
@Items_Per_Page INT = 10,
@Supplier_Id INT = NULL,
@Site_Id INT = NULL,
@Search_Term NVARCHAR(128) = NULL

with cte as (
    select distinct Product_Id
    FROM Product P
    LEFT JOIN Supplier_Product SUP ON P.Product_Id = SUP.Product_Id
    LEFT JOIN Site_Product SP ON P.Product_Id = SP.Product_Id
    WHERE 
        (SUP.Supplier_Id = @Supplier_Id OR @Supplier_Id IS NULL) AND
        (SP.Site_Id = @Site_Id OR @Site_Id IS NULL) AND
        (P.Product_Name LIKE ('%' + @Search_Term + '%') OR @Search_Term IS NULL)
    )

select P.Container_Noun, P.Open_Noun, P.Packaged, P.Product_Id, P.Product_Name, P.Quantity_Per_Package, P.Volume
SUP.Price, SUP.Supplier_Id, SUP.Supplier_Name,
SP.Site_Id, SP.Site_Name
FROM Product P
INNER JOIN (select Product_ID from cte ORDER BY Product_Id OFFSET @Items_Per_Page *  (@Current_Page - 1) ROWS FETCH NEXT @Items_Per_Page ROWS ONLY) PF ON P.Product_Id = PF.Product_Id
LEFT JOIN Supplier_Product SUP ON P.Product_Id = SUP.Product_Id
LEFT JOIN Site_Product SP ON P.Product_Id = SP.Product_Id
WHERE 
    (SUP.Supplier_Id = @Supplier_Id OR @Supplier_Id IS NULL) AND
    (SP.Site_Id = @Site_Id OR @Site_Id IS NULL) AND
    (P.Product_Name LIKE ('%' + @Search_Term + '%') OR @Search_Term IS NULL)
所以这里的技巧是首先获得10个不同的产品Id,然后使用它们在原始查询中过滤结果


如果您有任何问题,请告诉我。

因此,如果产品1有多个供应商和多个site_产品,您将如何定义其中哪一个与产品1相关?它们都是相关的。我想全部退回,但只退回按产品字母顺序排列的前10个产品,我知道会有重复的产品,我想全部退回,但只退回条件中的前10个产品。您可以使用嵌套查询获得前10个产品,并使用该查询连接到其余表。我不确定如何实现该功能,当我还需要根据供应商和站点进行筛选时。我不确定您使用的是哪种SQL,偏移行和获取下一行不是MS-SQL的,是MySql吗?谢谢您的帮助,我刚刚离开工作,但我明天第一件事就是做一个旋转:)。不能让这件事最终结束,所以回到家里,它很有魅力。如果可以的话,我会投更多的票!