不同的用户类型/对象在同一个表中拥有内容 - 如何?

Sea*_*anD 5 database schema database-design

知道如何将不同的物体联系在一起吗?我试图实现的用例是评论通常由用户拥有.所以我有一个user_id.但我也有公司页面,公司在其页面上拥有内容,因此所有者是company_id.(哪个是几个用户的管理员)

一种方法是有2个表user_comments和company_comments但问题是,然后我需要每个对象的2个表,如果我添加更多的用户类型,然后我需要多个表.我想要实现的是1个表,它具有:

comment_id PK  
owner_id (user id or company id or etc...)  - fk?
Run Code Online (Sandbox Code Playgroud)

所以,假设我创建一个所有者表只是为了将所有用户类型链接在一起,列将是什么将这些全部放入或有其他方式?

Mik*_*ll' 8

人和组织是超类型/子类型关系中的一个很好的例子.它们并不完全相同,但它们并不完全不同.它们共享许多属性.人员和组织都有地址和电话号码,人员和组织都可以成为诉讼中的原告和被告,人员和组织都可以在您的系统中显然拥有评论.

要在SQL dbms中实现此功能,请将人员和组织共有的列放在一个名为"Parties"的表中.人们独有的列在人们的桌子上; 组织特有的列在组织表中.使用视图(每个子类型一个)来隐藏实现细节; 您的客户使用视图而不是表.

您可以使用超类型表"派对"中的密钥作为您的评论的所有者.(我认为.)

这是一个简化的例子.

create table parties (
    party_id integer not null unique,
    party_type char(1) not null check (party_type in ('I', 'O')),
    party_name varchar(10) not null unique,
    primary key (party_id, party_type)
);

insert into parties values (1,'I', 'Mike');
insert into parties values (2,'I', 'Sherry');
insert into parties values (3,'O', 'Vandelay');

-- For "persons", a Subtype of "parties"
create table pers (
    party_id integer not null unique,
    party_type char(1) not null default 'I' check (party_type = 'I'),
    height_inches integer not null check (height_inches between 24 and 108),
    primary key (party_id),
    foreign key (party_id, party_type) references parties (party_id, party_type)
);

insert into pers values (1, 'I', 72);
insert into pers values (2, 'I', 60);

-- For "organizations", a subtype of "parties"
create table org (
    party_id integer not null unique,
    party_type CHAR(1) not null default 'O' check (party_type = 'O'),
    ein CHAR(10), -- In US, federal Employer Identification Number
    primary key (party_id),
    foreign key (party_id, party_type) references parties (party_id, party_type)
);

insert into org values (3, 'O', '00-0000000');

create view people as
select t1.party_id, t1.party_name, t2.height_inches
from parties t1
inner join pers t2 on (t1.party_id = t2.party_id);

create view organizations as 
select t1.party_id, t1.party_name, t2.ein
from parties t1
inner join org t2 on (t1.party_id = t2.party_id);
Run Code Online (Sandbox Code Playgroud)

使用dbms提供的任何功能使视图可更新.(可能触发.)然后应用程序代码可以插入到适当的视图中.

  • *"问题是,各方表仍然允许(4,'我','x')和(4,'O','y')"*:不,它不是.试试吧.(对party.party_id有一个独特的约束.)"party_type"列是克服SQL缺陷所必需的.关系模型不需要它,并且支持`CREATE ASSERTION`的SQL dbms不需要它.但是没有支持断言的SQL dbms. (2认同)