Zim*_*Zim 3 php sql database many-to-many
由于只有一些以前的数据库经验,并且没有正式的教育,我对如何建模(以及在PHP中检索我需要的数据)感到有些困惑.这就是我想要建模的:
对于我网站上的每个项目,允许有多个标签,如文件,上传,php,递归等.但是标签是可重复使用的,我可以有两个不同的项目,每个都可以有php标签.
我一直在努力阅读如何做到这一点,以及缺乏经验或其他我不知道的事情,但我似乎无法理解这个概念.显然你需要一个将两者连接在一起的中间表?
此外,一旦我建立了这种关系并定义了表格,我将如何执行以下操作: - 检索具有特定标记的所有项目? - 检索一个项目的所有标签?
感谢您的帮助,如果有人可以列出任何进一步的阅读,以加强我对这个概念的理解,这将是伟大的.
数据库部分很简单.这只是一个示例,因此您可以看到db的外观,而不是任何特定的SQL引擎查询.
CREATE TABLE posts (
id INT PRIMARY KEY,
subject VARCHAR(100),
body TEXT
)
CREATE TABLE tags (
id INT PRIMARY KEY,
name VARCHAR(50)
)
CREATE TABLE post_tags (
post_id INT,
tag_id INT,
FOREIGN KEY (post_id) REFERENCES posts (id),
FOREIGN KEY (tag_id) REFERENCES posts (id)
)
Run Code Online (Sandbox Code Playgroud)
要获取带有yourTag标记的项目,您只需运行此类查询
SELECT P.*
FROM posts P
LEFT JOIN post_tags PT ON (PT.post_id = P.id)
LEFT JOIN tags T ON (T.id = PT.tag_id)
WHERE T.name = 'yourTag';
Run Code Online (Sandbox Code Playgroud)
要获取与id相关的标签,123请运行此查询:
SELECT T.*
FROM tags T
LEFT JOIN post_tags PT ON (T.id = PT.tag_id)
LEFT JOIN posts P ON (PT.post_id = P.id)
WHERE P.id = 123;
Run Code Online (Sandbox Code Playgroud)
对于PHP部分,您可以使用框架.许多(如果不是全部)框架可以轻松地模拟这种关系.例如在CakePHP中这样做:
class Post extends AppModel {
$useTable = 'posts';
$hasAndBelongsToMany = array(
'Tag' => array(
'className' => 'Tag'
'joinTable' => 'post_tags'
'foreignKey' => 'post_id'
'associationForeignKey' => 'tag_id'
)
);
}
class Tag extends AppModel {
$useTable = 'tags';
$hasAndBelongsToMany = array(
'Post' => array(
'className' => 'Post'
'joinTable' => 'post_tags'
'foreignKey' => 'tag_id'
'associationForeignKey' => 'post_id'
)
);
}
Run Code Online (Sandbox Code Playgroud)
您应该使用中间表来关联这两个实体:
-------- 1:n ------------ --------- | ITEM |-¦---------<| ITEM_TAG | n:1 | TAG | | Id | | ItemId |>-------¦-| Id | | Name | | TagId | | Name | ¯¯¯¯¯¯¯¯ ¯¯¯¯¯¯¯¯¯¯¯¯ ¯¯¯¯¯¯¯¯¯
然后,为了查询数据,您应该在select语句中加入表:
标签" FooTag " 中的所有项目
SELECT item.* FROM item
JOIN item_tag on item.id = item_tag.itemId
JOIN tag on item_tag.tagId = tag.id
WHERE tag.Name = 'FooTag'
Run Code Online (Sandbox Code Playgroud)
名称为" FooItem " 的项目的所有标签
SELECT tag.* FROM tag
JOIN item_tag on tag.id = item_tag.tagId
JOIN item on item_tag.itemId = item.id
WHERE item.Name = 'FooItem'
Run Code Online (Sandbox Code Playgroud)