需要使用SQL查询
说帮助我有2个表:需要使用SQL查询
Person
- Id
- Name
PersonAttribute
- Id
- PersonId
- Name
- Value
而且,让我们说,每个人有2种属性(比如,性别和年龄)。样本的记录是这样的:
Person->Id = 1
Person->Name = 'John Doe'
PersonAttribute->Id = 1
PersonAttribute->PersonId = 1
PersonAttribute->Name = 'Gender'
PersonAttribute->Value = 'Male'
PersonAttribute->Id = 2
PersonAttribute->PersonId = 1
PersonAttribute->Name = 'Age'
PersonAttribute->Value = '30'
问题:我该如何查询该这样,我得到这样一个结果:
“李四”,“男”,“30”
SELECT p.name, p1.Value, p2.Value
FROM Person p, PersonAttribute p1, PersonAttribute p2
WHERE p.Id = p1.PersonId AND p.Id = p2.PersonId
AND p1.Name = 'Gender' AND p2.Name = 'Age'
我认为你需要重新设计你的架构。 为什么不呢?
Person
- Id
- Name
- Gender
- Birthday
...
+1完全同意。看起来年龄存储在PersonAttribute-> Value字符串列中,以及诸如“Male”之类的内容(并且您指出这应该是派生出来的) – 2010-06-02 06:33:46
我不同意。 OP设计了一个通用属性模式,可能使用户可以定义他们自己的属性并分配他们自己的值。不过,他的例子是一个很差的例子。 – Timothy 2010-06-02 06:38:53
@ msi77&@martinsmith:模式要求实体A具有0个或更多属性。 “人”的例子就是这样一个例子。我用它来简化我的问题并获得更快的响应。 – *Newbie 2010-06-02 06:49:40
SELECT Name, g.Value, a.Value
FROM Person,
PersonAttribute g INNER JOIN ON g.Name = "Gender",
PersonAttribute a INNER JOIN ON a.Name = "Age"
SELECT p.Name,g.Value,a.value中
FROM人员P INNER JOIN PersonAttribute克ON p.Id = g.Id AND g.Name = “性别”
INNER JOIN PersonAttribute a ON p.Id = a.Id AND a.Name =“Age”
存储名称值对提供了灵活性,但查询非常麻烦。 在http://www.simple-talk.com/community/blogs/philfactor/archive/2008/05/29/56525.aspx
+1当我看到这样的模式时,我总是想到那篇文章。 – 2010-06-02 06:47:16
+1这确实是一个棘手的问题。从概念上讲,这太棒了,但实施是一个痛苦。 – Timothy 2010-06-03 07:42:42
看看有没有简单的方法来做到这一点。
透视表(已被另一个答复中提到)的概念基本上是你在找什么,但透视表需要你知道你要使用的列的名称。很显然,当你想利用这种桌子设计的力量时,这是一个问题!
在我以前的生活,我只是看中了列的X号,如20-30,如果他们不存在,则该行集包含了一堆空值。没什么大不了。
select piv.name,
max(case piv.a_name when 'Gender' then piv.a_value else null end) as Gender,
max(case piv.a_name when 'Age' then piv.a_value else null end) as Age,
max(case piv.a_name when 'Hobby' then piv.a_value else null end) as Hobby
from
(select p.name as name, pa.name as a_name, pa.value as a_value
from person p, personattribute pa
where p.id = pa.personid) piv
group by piv.name
这将产生像这样的输出:
name | gender | age | hobby
-----------+--------+-----+---------
Bob Swift | Male | | Reading
John Doe | Male | 30 |
(2 rows)
这是非常该死接近你在找什么。我会将剩下的部分留给应用层。
我也强烈建议您包含属性名称作为返回值的一部分,提供上下文的值。
这类所谓的实体属性的设计往往最终不得不依靠特定的服务器功能,存储过程和硬编码查询的组合。
这不能缩放以提取N个通用属性及其值。 – Timothy 2010-06-02 06:39:35