可能有更优雅的解决方案,但无论如何......
DROP TABLE IF EXISTS categories;
CREATE TABLE categories
(id INT NOT NULL AUTO_INCREMENT PRIMARY KEY
,name VARCHAR(12) NOT NULL UNIQUE
);
INSERT INTO categories VALUES
(1 ,'Foo'),(2,'Bar'),(3,'Boo');
DROP TABLE IF EXISTS companies;
CREATE TABLE companies
(id INT NOT NULL AUTO_INCREMENT PRIMARY KEY
,name VARCHAR(12) NOT NULL UNIQUE
);
INSERT INTO companies VALUES
(1,'Company1'),(2,'Company2'),(3,'Company3');;
DROP TABLE IF EXISTS company_category;
CREATE TABLE company_category
(company_id INT NOT NULL,category_id INT NOT NULL,PRIMARY KEY(company_id,category_id));
INSERT INTO company_category VALUES (1 ,1),(1 ,2),(2 ,2);
SELECT o.id company_id
, o.name company_name
, a.id category_id
, a.name cateory_name
, CASE WHEN oa.company_id IS NOT NULL THEN ' checked' ELSE '' END checked
FROM companies o
JOIN categories a
LEFT
JOIN company_category oa
ON oa.company_id = o.id
AND oa.category_id = a.id;
+------------+--------------+-------------+--------------+----------+
| company_id | company_name | category_id | cateory_name | checked |
+------------+--------------+-------------+--------------+----------+
| 1 | Company1 | 1 | Foo | checked |
| 2 | Company2 | 1 | Foo | |
| 3 | Company3 | 1 | Foo | |
| 1 | Company1 | 2 | Bar | checked |
| 2 | Company2 | 2 | Bar | checked |
| 3 | Company3 | 2 | Bar | |
| 1 | Company1 | 3 | Boo | |
| 2 | Company2 | 3 | Boo | |
| 3 | Company3 | 3 | Boo | |
+------------+--------------+-------------+--------------+----------+
http://www.sqlfiddle.com/#!2/11e6e/1