Database design 好友列表:关系数据库表设计

Database design 好友列表:关系数据库表设计,database-design,relational-database,jointable,Database Design,Relational Database,Jointable,因此,好友列表的现代概念: 假设我们有一张名为Person的桌子。现在,这个人需要有很多好友(其中每个好友都在Person类中)。构造关系最明显的方法是通过联接表。 i、 e 但是,当用户想要查看好友列表时,程序必须检查“person1_id”和“person2_id”列才能找到他们的所有好友 这是实现此类表的适当方法,还是最好添加两次记录。。i、 e buddyID person1_id person2_id 0 1 2 1 2

因此,好友列表的现代概念:
假设我们有一张名为Person的桌子。现在,这个人需要有很多好友(其中每个好友都在Person类中)。构造关系最明显的方法是通过联接表。 i、 e

但是,当用户想要查看好友列表时,程序必须检查“person1_id”和“person2_id”列才能找到他们的所有好友

这是实现此类表的适当方法,还是最好添加两次记录。。i、 e

buddyID   person1_id   person2_id
0         1            2
1         2            1
因此,只需搜索一列


提前感谢。

这里有几种可能的情况

首先,您需要确定伙伴关系是否可以是一种方式。如果B不是A的好友,A可以成为B的好友吗?我想不会,但这是值得明确的


常识会建议你查询更多而不是更新关系。因此,请为此优化您的数据。创建好友关系时,创建两个recrods:a到B和B到a。这将使查询变得简单。所以,是的,按照您已经考虑过的两条记录进行处理。

这是一个多对多关系,需要一个关系表

create table Person (
   person_id int not null primary key,
   username varchar(100) not null,
   ... other_cols ...
)


create table Buddy (
   person_id1 int not null,
   person_id2 int not null,
   primary key (person_id1, person_id2),
   foreign key (person_id1) reference Person (person_id),
   foreign key (person_id2) reference Person (person_id)
)
显然,Person表将为每个人包含一行。它将包含任何关于好友的数据,因为这将使它非规范化。相反,Buddy表将包含人员之间的关系

假设Person表中有类似的内容:

person_id    username
1            George
2            Henry
3            Jody
4            Cara
亨利和卡拉是好朋友,乔治和卡拉也是:

person_id1   person_id2
2            4
1            4
如果需要使关系不是隐式相互的,则需要添加额外的行以使其显式。现在让我们假设亨利认为卡拉是一个伙伴,卡拉同样认为亨利是一个伙伴,而乔治认为卡拉是一个伙伴,但卡拉没有回报乔治:

person_id1   person_id2
2            4
4            2
1            4
<

失踪的4,1表示卡拉不认为乔治是好友。这使事情非常干净,避免了数据异常。您可以调整关系,而无需处理人员数据。此外,您还可以在外键上定义一个delete cascades规则,以便删除Person将自动为您删除所有关联的关系。相反,您可能希望防止这种情况,在这种情况下,您可以在外键上指定restrict(默认值),以防止删除仍定义了关系的人员

查询也很容易:

Cara有多少好友(假设好友列表的关系是隐式的):

对于不暗示关系的情况,最好改用如下方式重命名列:

person_id   considers_as_buddy_id
2           4
4           2
1           4
4           3

select count(*) from Person P
                join Buddy B on P.person_id = B.person_id
 where name = 'Cara'
这将返回卡拉认为是好友的人数。在这种情况下2。虽然Jody不认为Cara是好友,但要了解彼此的关系,你可以这样做:

select count(*) from Person P
                join Buddy B on P.person_id = B.person_id and 
                                B.considers_as_buddy_id = P.person_id
 where name = 'Cara'

对这很有道理。我应该考虑一下。谢谢,谢谢你的详细回答。这两个都非常有用。在一个普通的MySql盒上,如果有人有20000个好友,并且想在<1秒钟内把整个列表拉到那里,这是一个可用的设计吗?
person_id   considers_as_buddy_id
2           4
4           2
1           4
4           3

select count(*) from Person P
                join Buddy B on P.person_id = B.person_id
 where name = 'Cara'
select count(*) from Person P
                join Buddy B on P.person_id = B.person_id and 
                                B.considers_as_buddy_id = P.person_id
 where name = 'Cara'