提问者:小点点

对于键/值数据库结构,是否可以将键用作列,将值用作值? [副本]


我需要从mysql-keyvalue表中查询一些数据,但我希望得到一个“普通”表作为结果,并将指定的键作为列。

我的表示例:

USERS
ID, user_id, key,        value 
1   1        first_name  Peter
2   1        last_name   Sputnick
3   2        first_name  Jan
4   2        last_name   Putgraver
5   2        country     Netherlands

我希望将此作为查询结果:

USERS
ID, first_name, last_name
1   Peter       Sputnick
2   Jan         Putgraaf

有没有一个好的,高效的方法来实现这一点? 注意,我不想在结果中包含国家/地区字段。

我需要这个,因为我需要将这个数据与来自另一个表的数据联接起来,而且我不想为我需要的每个字段使用一个子查询。 所以我不想做这样的事情:

SELECT *,
(SELECT value 
  FROM users 
  WHERE user_id = o.user_id 
    AND key = first_name),
(SELECT value 
  FROM users 
  WHERE user_id = o.user_id 
    AND key = last_name),
FROM orders o

共2个答案

匿名用户

对于这种情况,必须使用条件聚合,

CREATE TABLE USERS (
  `ID` VARCHAR(6),
  `user_id` VARCHAR(9),
  `key` VARCHAR(10),
  `value` VARCHAR(11)
);
INSERT INTO USERS
  (`ID`, `user_id`, `key`, `value`)
VALUES
  ('1', '1', 'first_name', 'Peter'),
  ('2' ,  '1', 'last_name', 'Sputnick'),
  ('3', '2', 'first_name', 'Jan'),
  ('4', '2', 'last_name', 'Putgraver'),
  ('5', '2', 'country', 'Netherlands');
SELECT user_id
, MAX(IF(`key` ='first_name',`value`,NULL )) fisrt_name
, MAX(IF(`key` ='last_name',`value`,NULL )) last_name
FROM USERS
GROUP BY user_id;
user_id | fisrt_name | last_name
:------ | :--------- | :--------
1       | Peter      | Sputnick 
2       | Jan        | Putgraver

db<;>此处小提琴

如果需要所有键,则必须使用透视表

匿名用户

您可以使用条件聚合:

select 
    id,
    max(case when key = 'fist_name' then value end) first_name,
    max(case when key = 'last_name' then value end) last_name
from users
group by id