我有一张包含以下数据的表格。
表名:myTable
prodID catNo variable1 variable2
1 20 Cat Blue
2 10 Cat Red
2 15 Cat Green
2 20 Cat Black
3 20 Cat Yellow
4 10 Cat Orange
4 15 Cat Brown
4 20 Cat Black
5 30 Cat Pink
我希望能够从myTable中选择以下内容的所有列:"( prodID = 2 且 catNo = 10 ) AND( prodID = 2 且 catNo = 15 )"。因此,只有在满足两个条件时才获得两行的结果,并且如果两行都不存在则不返回任何结果。 所以我的结果表将如下所示。
表名:结果
prodID catNo variable1 variable2
2 10 Cat Red
2 15 Cat Green
我尝试使用条件if语句,但似乎无法让它们在sql中运行。我目前的解决方案是使用prodID = 2返回所有行,然后使用php执行if语句来决定要显示的内容,但这不会影响我设计用于显示结果的分页作为我的limit会扭曲每页的结果数。 我知道我可以使用'计数行= 2'但我不确定如何说出来。
答案 0 :(得分:3)
如果你想在catNo(10,15)中找到记录时得到结果,但如果你在(10,12)中寻找catNo,那么也要返回0结果
SELECT * FROM `myTable`
WHERE (`prodID` = 2 AND `catNo` IN (10,15))
AND (SELECT COUNT(`catNo`) FROM `myTable` WHERE `prodID` = 2 AND `catNo` IN (10,15))>1;
对于三个CatNo&#39>
SELECT * FROM `myTable`
WHERE (`prodID` = 4 AND `catNo` IN (10,15,20))
AND (SELECT COUNT(`catNo`) FROM `myTable` WHERE `prodID` = 4 AND `catNo` IN (10,15,20))>2;
答案 1 :(得分:2)
要匹配同一产品的两个类别,您可以这样做
select t.*
from table1 t
join (
select prodID
from table1
where catNo in (10,15)
and prodID = 2
group by prodID
having count(distinct catNo ) = 2
) t2
using(prodID)
where t.catNo in (10,15)
答案 2 :(得分:1)
使用以下SQL查询。
SELECT * FROM myTable where prodID = 2 and (catNo = 10 OR catNo = 15)
希望这有助于你
答案 3 :(得分:1)
试试这个会起作用:
SELECT * FROM `myTable` WHERE `prodID` = '2' AND `catNo` IN ('10','15')
答案 4 :(得分:0)
条件应为(prodID = 2且catNo = 10)或(prodID = 2且catNo = 15)
答案 5 :(得分:0)
SELECT DISTINCT a.*,b.catNo,c.catNo FROM myTable AS a
JOIN mytable AS b ON b.prodID=a.prodID
JOIN mytable AS c ON c.prodID=a.prodID
WHERE a.prodID=2 AND b.catNo=10
AND c.catNo=15;
这个有用了。这个问题非常棘手。
答案 6 :(得分:0)
发布的大多数解决方案都缺少关于什么都不返回的部分,除非满足条件。因此,如果满足一个且只有一个条件,大多数解决方案将失败,因为它们仍将返回一行而不是一行。
假设您希望能够检查任何数量的WHERE条件,而不仅仅是两个,您可以使用基于子查询的解决方案。
使用此方法,您可以在输出之前检查结果集中的合格行数。有几种方法可以做到这一点,但想法是将符合条件的行数与预期的行数进行比较。如果匹配,则输出行。如果它们不匹配,则返回空结果集。
M Khalid Junaid已经发布了一个使用组的解决方案,其中包含子查询中的条件,以检查结果集大小是否为2.此解决方案适用于您的特定示例以及其他类似示例。如果您的WHERE条件变得更复杂或变化,可能不会因为它依赖于每个WHERE条件中的ProdID相同,但是主体是声音。此外,这种特殊方法要求对源表处理WHERE条件两次,而下面的一次仅执行一次。对于非常大的表和/或许多WHERE条件,此方法应该更有效。
您可以像在其他示例中一样直接在FROM条件中构建子查询,也可以通过WITH语句构造子查询。我在这里使用了后者,因为它更清楚地显示了正在发生的事情:
With ResultSet as (select * from myTable
where (prodID = 2 AND catNo = 10) OR (prodID = 2 AND catNo = 15)), -- your WHERE condition
TotalRows as (select COUNT(*) as TRows from ResultSet) -- count of result set
select ResultSet.*
from ResultSet
inner join TotalRows on 1=1 -- force the join to work no matter what the tables contain
where TRows = 2 -- this is where you check against how many result rows you expect
" ResultSet"子查询是WHERE原因所在的位置,它可以根据需要简单或复杂。 " TotalRows"计算结果集,因此只包含一行。然后,您可以将子查询连接在一起,但如果结果集计数(TRows)与之后的预期行大小匹配,则只输出前者的行。
答案 7 :(得分:0)
您可以尝试编写一个函数。它很长但很容易理解
DROP FUNCTION getIt();
CREATE OR REPLACE FUNCTION getIt()
RETURNS TABLE (prodID INTEGER, catNo INTEGER, variable1 TEXT, variable2 TEXT) AS
$BODY$
BEGIN
IF (CAST ((SELECT "prodID"
FROM "myTable"
where "prodID"=2 and "catNo" = 10) AS INTEGER)>0 AND CAST ((SELECT "prodID"
FROM "myTable"
where "prodID"=2 and "catNo" = 15) AS INTEGER)>0)
THEN RETURN QUERY SELECT *
FROM "myTable"
where "prodID"=2 and ("catNo" = 10 or "catNo" = 15 );
END IF;
END;
$BODY$
LANGUAGE 'plpgsql';
SELECT * FROM getIt();
可以参数化
DROP FUNCTION getIt(pid integer, cid1 integer, cid2 integer);
CREATE OR REPLACE FUNCTION getIt(pid integer, cid1 integer, cid2 integer)
RETURNS TABLE (prodID INTEGER, catNo INTEGER, variable1 TEXT, variable2 TEXT) AS
$BODY$
BEGIN
IF (CAST ((SELECT "prodID"
FROM "myTable"
where "prodID"=$1 and "catNo" = $2) AS INTEGER)>0 AND CAST ((SELECT "prodID"
FROM "myTable"
where "prodID"=$1 and "catNo" = $3) AS INTEGER)>0)
THEN RETURN QUERY SELECT *
FROM "myTable"
where "prodID"=$1 and ("catNo" = $2 or "catNo" = $3 );
END IF;
END;
$BODY$
LANGUAGE 'plpgsql';
SELECT * FROM getIt(2, 10, 15);
答案 8 :(得分:-1)
谢谢你M Khalid Junaid's answer的作品。我设法提出了一个不需要加入的解决方案,像我这样的非常大的桌子将会很慢:
select *
from myTable
where ((prodID = 2 and catNo = 10) or (prodID = 2 and catNo = 15))
group by catNo
having (
select count(distinct(catNo))
from myTable
where ((prodID = 2 and catNo = 10) or (prodID = 2 and catNo = 15))
)=2;