Php 根据多个类别动态匹配项目
鉴于下表:Php 根据多个类别动态匹配项目,php,mysql,sql,database,pdo,Php,Mysql,Sql,Database,Pdo,鉴于下表: CREATE TABLE catalog_categories ( cat_id INTEGER UNSIGNED NOT NULL AUTO_INCREMENT, parent_id INTEGER UNSIGNED DEFAULT NULL, title VARCHAR(255) NOT NULL, valid TINYINT(1) UNSIGNED NOT NULL DEFAULT 1, PRIMARY KEY(cat_id), FOREIGN KEY
CREATE TABLE catalog_categories (
cat_id INTEGER UNSIGNED NOT NULL AUTO_INCREMENT,
parent_id INTEGER UNSIGNED DEFAULT NULL,
title VARCHAR(255) NOT NULL,
valid TINYINT(1) UNSIGNED NOT NULL DEFAULT 1,
PRIMARY KEY(cat_id),
FOREIGN KEY (parent_id)
REFERENCES catalog_categories(cat_id)
);
CREATE TABLE catalog_item_categories (
item_id INTEGER UNSIGNED NOT NULL,
cat_id INTEGER UNSIGNED NOT NULL,
valid TINYINT(1) UNSIGNED NOT NULL DEFAULT 1,
FOREIGN KEY (item_id)
REFERENCES catalog_items(item_id),
FOREIGN KEY (cat_id)
REFERENCES catalog_categories(cat_id)
);
和多维数组作为输入,其中key=>parent\u id,value=>cat\u id
["categories"]=>
array(2) {
[1]=>
array(2) {
[0]=>
string(1) "5"
[1]=>
string(1) "6"
}
[2]=>
array(1) {
[0]=>
string(2) "12"
}
}
我试图只选择与提供的类别匹配的项目
SELECT a.item_id
FROM catalog_items AS a
JOIN catalog_item_categories AS b ON a.item_id = b.item_id
JOIN catalog_categories AS c ON b.cat_id = c.cat_id AND c.parent_id = 1 AND c.cat_id IN ('5', '6')
JOIN catalog_categories AS d ON b.cat_id = d.cat_id AND d.parent_id = 2 AND d.cat_id IN ('12')
WHERE a.valid = TRUE
AND b.valid = TRUE
AND c.valid = TRUE
AND d.valid = TRUE
这是我硬编码的尝试,但是有没有更好的方法,或者我如何动态地构建这个查询?如果我事先不知道会有多少个
父=>子关系。您可以通过聚合查询来实现这一点,聚合查询的构造可能更简单:
select cic.item_id
from catalog_item_categories cic
group by cic.item_id
where sum(cic.cat_id in (5, 6) and cic.valid = 1) > 0 and
sum(cic.cat_id in (12) and cic.valid = 1) > 0;
考虑通过类别循环,使用动态PHP字符串构建SQL查询。当然,如果数组数据来自用户输入,请使用以下选项,而不是concateration:
$categories = [
1 => array("5","6"),
2 => array("12")
];
$sql = "SELECT a.item_id
FROM catalog_items AS a
JOIN catalog_item_categories AS b ON a.item_id = b.item_id";
$i = 1;
foreach($categories as $k=>$v){
$cats = implode(",", $v);
$sql = $sql."
JOIN catalog_categories AS c$i ON b.cat_id = c$i.cat_id AND c$i.parent_id = $k
AND c$i.cat_id IN ($cats) AND c$i.valid = TRUE";
$i = $i + 1;
}
$sql = $sql.
"\nWHERE a.valid = TRUE AND b.valid = TRUE";
echo $sql;
输出
选择一个项目\u id
从目录_项作为
在a.item\u id=b.item\u id上将目录\u item\u类别作为b连接
在b.cat_id=c1.cat_id和c1.parent_id=1上以c1的形式连接目录_类别
和c1.cat_id IN(5,6)和c1.valid=TRUE
在b.cat_id=c2.cat_id和c2.parent_id=2上以c2的形式加入目录_类别
和c2.cat_id IN(12)和c2.valid=TRUE
其中a.valid=TRUE和b.valid=TRUE
我没有家长id
。你能提供样本数据和期望的结果吗?类别可以有子类别…我有点困惑。此解决方案不检查项目是否有效(您遗漏了目录项目
),并且它忽略了用于将子项与其父类别关联的父项id
。您还遗漏了目录类别
,因此它不检查类别是否有效。