我有以下查询,它只选择特征ID。 4,5 和 7:
SELECT
p.id_product,
fvl.value,
fvp.position,
fv.id_feature
FROM
ps_feature_product fp
INNER JOIN ps_product p ON p.id_product = fp.id_product
INNER JOIN ps_feature_value fv ON fp.id_feature_value = fv.id_feature_value
INNER JOIN ps_feature_value_position fvp ON fv.id_feature_value = fvp.id_feature_value
INNER JOIN ps_feature_value_lang fvl ON fv.id_feature_value = fvl.id_feature_value
WHERE
fvl.id_lang = 1
AND
fp.id_feature IN ( 4,5,7 )
需要根据每个特征添加三个条件。像...
WHERE
fp.id_feature = 4
AND
fp.feature_value_position >= 50
-- and so on (position can be grater or lower).
我试过以下:
SELECT
p.id_product,
fvl.value,
fvp.position,
fv.id_feature
FROM
ps_feature_product fp
INNER JOIN ps_product p ON p.id_product = fp.id_product
INNER JOIN ps_feature_value fv ON fp.id_feature_value = fv.id_feature_value
INNER JOIN ps_feature_value_position fvp ON fv.id_feature_value = fvp.id_feature_value
INNER JOIN ps_feature_value_lang fvl ON fv.id_feature_value = fvl.id_feature_value
WHERE
fvl.id_lang = 1
AND
(
(fv.id_feature = 4 AND fvp.position >= 100)
AND
(fv.id_feature = 5 AND fvp.position >= 20)
AND
(fv.id_feature = 7 AND fvp.position >= 20)
)
但我猜,这在理论上是行不通的。实现这一目标的最佳方法是什么?
值得一提的是,这三个条件都应该满足。就像,没有找到带有
id_feature = 5 AND fvp.position >= 80
的产品,它不应该产生任何结果 - 即使例如if fv.id_feature = 7 AND fvp.position >= 20
包含产品。
我也试过用 OR 而不是 AND 像这样:
WHERE
fvl.id_lang = 1
AND
(
(fv.id_feature = 4 AND fvp.position >= 100)
OR
(fv.id_feature = 5 AND fvp.position >= 20)
OR
(fv.id_feature = 7 AND fvp.position >= 20)
)
但是如果满足这三个条件之一,这将输出结果。它应该基于所有这些。
希望这是有道理的。
仅使用
AND
和OR
,但保留IN
运算符,使查询引擎更容易保持查询SARGable:
WHERE
fvl.id_lang = 1
AND
fv.id_feature IN ( 4, 5, 7 )
AND
(
( fv.id_feature = 4 AND fvp.position >= 100 )
OR
( fv.id_feature = 5 AND fvp.position >= 20 )
OR
( fv.id_feature = 7 AND fvp.position >= 20 )
)
尽管
CASE <expr> WHEN <const-value>
表达式也有效,但您需要在嵌套的 fvp.position >= x
:中重复
CASE WHEN
WHERE
fvl.id_lang = 1
AND
CASE fv.id_feature
WHEN 4 THEN ( CASE WHEN fvp.position >= 100 THEN 1 END )
WHEN 5 THEN ( CASE WHEN fvp.position >= 20 THEN 1 END )
WHEN 7 THEN ( CASE WHEN fvp.position >= 20 THEN 1 END )
END
或作为
CASE WHEN <expr> THEN
:
WHERE
fvl.id_lang = 1
AND
CASE
WHEN fv.id_feature = 4 AND fvp.position >= 100 THEN 1 END )
WHEN fv.id_feature = 5 AND fvp.position >= 20 THEN 1 END )
WHEN fv.id_feature = 7 AND fvp.position >= 20 THEN 1 END )
END
一如既往,检查您的查询计划以确保它仍在适当地使用您的索引。