Mysql查询获取逗号分隔的id数据的详细信息

时间:2012-12-02 14:52:06

标签: mysql

我有2个表,项目和成员:

CREATE TABLE IF NOT EXISTS `items` (
`id` int(5) NOT NULL AUTO_INCREMENT,
`name` varchar(255) NOT NULL,
`member` varchar(255) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;

CREATE TABLE IF NOT EXISTS `members` (
  `id` int(5) NOT NULL AUTO_INCREMENT,
  `name` varchar(255) NOT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;

如果我在items内有记录,例如

,该怎么办?
INSERT INTO  `test`.`items` (
`id` ,
`name` ,
`member`
)
VALUES (
NULL ,  'xxxx',  '1, 2, 3'
);
members中的

INSERT INTO `members` (`id`, `name`) VALUES
(1, 'asdf'),
(2, 'qwert'),
(3, 'uiop'),
(4, 'jkl;');

我希望用items.member显示members.name数据,例如1#asdf, 2#qwert, 3#uiop ??

我尝试了以下查询,

SELECT items.id, items.name, GROUP_CONCAT(CONCAT_WS('#', members.id, members.name) ) as member

FROM `items` 
LEFT JOIN members AS members on (members.id = items.member)
WHERE items.id = 1

但结果并不像我预期的那样。有没有其他方法通过一个调用查询显示数据?因为我现在正在使用PHP,所以我会爆炸items.member并逐个循环,以显示members.name

2 个答案:

答案 0 :(得分:3)

您可以考虑在加入条件中使用FIND_IN_SET()

FROM items JOIN members ON FIND_IN_SET(members.id, items.member)

但是,请注意FIND_IN_SET()的定义:

  

字符串列表是由以“,”字符分隔的子字符串组成的字符串。

因此items.member列不应包含任何空格(我想您可以使用FIND_IN_SET(members.id, REPLACE(items.member, ' ', '')) - 但随着数据库的增长,这将是非常昂贵的。)

真的,你应该 normalise你的架构:

CREATE TABLE memberItems (
  item_id   INT(5) NOT NULL,
  member_id INT(5) NOT NULL,
  FOREIGN KEY   item_id REFERENCES   items (id),
  FOREIGN KEY member_id REFERENCES members (id)
);

INSERT INTO memberItems
  (item_id, member_id)
SELECT items.id, members.id
FROM   items
  JOIN members ON FIND_IN_SET(members.id, REPLACE(items.member,' ',''))
;

ALTER TABLE items DROP member;

这既是索引友好的(因此可以非常有效地查询)并且数据库强制执行参照完整性。 然后你可以这样做:

FROM items JOIN memberItems ON memberItems.item_id = items.id
           JOIN members     ON members.id = memberItems.member_id

另请注意,使用GROUP_CONCAT()以这种方式将单独的记录组合成字符串通常是不明智的:您的应用程序应该准备循环遍历结果集以获取每个成员。

答案 1 :(得分:0)

请看一下这个样本:

SQLFIDDLE

您的查询似乎适用于您在问题中提到的内容......:)

SELECT I.ID, I.ITEM,
GROUP_CONCAT(CONCAT("#",M.ID,
M.NAME, " ")) AS MEMB

FROM ITEMS AS I
LEFT JOIN MEMBERS AS M
ON M.ID = I.MID
WHERE i.id = 1
;

收到的答案 此查询不适合您 - 因为您的架构似乎没有任何完整性......或适当的引用。此外,您的memeber ID由逗号分隔,在此答案中已被忽略。