MySQL:根据关系表

时间:2016-07-25 12:22:55

标签: mysql

我在这一点上有点迷失,我在基于其关系表的值在表上显示行时出现问题。我不知道该如何解决这个问题。我的预期结果如下:

预期结果

-- Expected Result #1: (user_id = 1 only, applied)
------  --------  -------  --------
    id  position  user_id  meta_key
------  --------  -------  --------
     1  Waiter          1  applied 
     2  Busboy     (NULL)  (NULL)  
     3  Driver     (NULL)  (NULL)  
     4  Chef            1  applied 
------  --------  -------  --------

-- Expected Result #2: Same as above except filtered by category IN(98)
------  --------  -------  --------
    id  position  user_id  meta_key
------  --------  -------  --------
     1  Waiter          1  applied    (uses category: 98, 99)
     2  Busboy     (NULL)  (NULL)     (uses category: 98)
     3  Driver     (NULL)  (NULL)     (uses category: 98)
------  --------  -------  --------

我的表格

Table 1: Position
------  --------  ---------
    id  position  user_id  
------  --------  ---------
     1  Waiter            1
     2  Busboy            1
     3  Driver            2
     4  Chef              3
------  --------  ---------

Table 2: Meta
------  -------  -----------  --------  ------------
    id  user_id  position_id  meta_key  meta_value  
------  -------  -----------  --------  ------------
     1        1            1  category  98          
     2        1            1  category  99          
     3        1            2  category  98          
     4        2            3  category  98          
     5        3            4  category  100          
     7        1            1  applied   1
     8        2            1  applied   1
     9        3            1  applied   1
    10        1            4  applied   1
------  -------  -----------  --------  ------------

在我的预期结果中,所有位置都会被显示,除非它被一个或多个类别过滤。用户基本上“应用”到位置,如果他们应用了user_id,则显示他们的user_id。但如果该条目来自他们不适用的职位,则该职位仍会显示,但user_id字段为NULL

MySQL可以做这样的事吗?我的初始查询能够完成第一个预期结果,但不能完成第二个按类别过滤的结果。

我的查询(user_id = 1)

SELECT pos.id, pos.position, meta.user_id, meta.meta_key
 FROM `position` pos
    LEFT JOIN meta ON pos.id = meta.position_id 
                  AND meta.meta_key = 'applied' 
                  AND meta.user_id = 1

SQL文件

SET @OLD_UNIQUE_CHECKS=@@UNIQUE_CHECKS, UNIQUE_CHECKS=0;
SET @OLD_FOREIGN_KEY_CHECKS=@@FOREIGN_KEY_CHECKS, FOREIGN_KEY_CHECKS=0;
SET @OLD_SQL_MODE=@@SQL_MODE, SQL_MODE='TRADITIONAL,ALLOW_INVALID_DATES';


-- -----------------------------------------------------
-- Table `position`
-- -----------------------------------------------------
DROP TABLE IF EXISTS `position` ;

CREATE TABLE IF NOT EXISTS `position` (
  `id` INT NOT NULL,
  `position` VARCHAR(191) NULL,
  `user_id` INT NULL,
  PRIMARY KEY (`id`))
ENGINE = InnoDB;


-- -----------------------------------------------------
-- Table `meta`
-- -----------------------------------------------------
DROP TABLE IF EXISTS `meta` ;

CREATE TABLE IF NOT EXISTS `meta` (
  `id` INT NOT NULL,
  `user_id` INT NULL,
  `position_id` INT NULL,
  `meta_key` VARCHAR(191) NULL,
  `meta_value` VARCHAR(191) NULL,
  PRIMARY KEY (`id`))
ENGINE = InnoDB;


SET SQL_MODE=@OLD_SQL_MODE;
SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS;
SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS;

-- -----------------------------------------------------
-- Data for table `position`
-- -----------------------------------------------------
START TRANSACTION;
INSERT INTO `position` (`id`, `position`, `user_id`) VALUES (1, 'Waiter', 1);
INSERT INTO `position` (`id`, `position`, `user_id`) VALUES (2, 'Busboy', 1);
INSERT INTO `position` (`id`, `position`, `user_id`) VALUES (3, 'Driver', 2);
INSERT INTO `position` (`id`, `position`, `user_id`) VALUES (4, 'Chef', 3);

COMMIT;


-- -----------------------------------------------------
-- Data for table `meta`
-- -----------------------------------------------------
START TRANSACTION;
INSERT INTO `meta` (`id`, `user_id`, `position_id`, `meta_key`, `meta_value`) VALUES (1, 1, 1, 'category', '98');
INSERT INTO `meta` (`id`, `user_id`, `position_id`, `meta_key`, `meta_value`) VALUES (2, 1, 1, 'category', '99');
INSERT INTO `meta` (`id`, `user_id`, `position_id`, `meta_key`, `meta_value`) VALUES (3, 1, 2, 'category', '98');
INSERT INTO `meta` (`id`, `user_id`, `position_id`, `meta_key`, `meta_value`) VALUES (4, 2, 3, 'category', '98');
INSERT INTO `meta` (`id`, `user_id`, `position_id`, `meta_key`, `meta_value`) VALUES (5, 3, 4, 'category', '100');
INSERT INTO `meta` (`id`, `user_id`, `position_id`, `meta_key`, `meta_value`) VALUES (7, 1, 1, 'applied', '1');
INSERT INTO `meta` (`id`, `user_id`, `position_id`, `meta_key`, `meta_value`) VALUES (8, 2, 1, 'applied', '1');
INSERT INTO `meta` (`id`, `user_id`, `position_id`, `meta_key`, `meta_value`) VALUES (9, 3, 1, 'applied', '1');
INSERT INTO `meta` (`id`, `user_id`, `position_id`, `meta_key`, `meta_value`) VALUES (10, 1, 4, 'applied', '1');

COMMIT;

1 个答案:

答案 0 :(得分:0)

要显示预期结果#2是可能的,一种方法是创建视图,并按类别过滤。

这些是我执行的命令。

MariaDB [test]>创建视图v作为SELECT pos.id,pos.position,meta.user_id,meta.meta_key FROM position pos LEFT JOIN meta ON pos.id = meta.position_id AND meta.meta_key =' applied&#39 ; AND meta.user_id = 1;

查询正常,0行受影响(0.03秒)

MariaDB [test]> select * from v where id in(从meta中选择position_id,其中meta_key =' category' and meta_value =' 98');

+ ---- + ---------- + --------- + ---------- +
| id |位置| user_id | meta_key |
+ ---- + ---------- + --------- + ---------- +
| 1 |服务员| 1 |申请|
| 2 | Busboy | NULL | NULL |
| 3 |司机| NULL | NULL |
+ ---- + ---------- + --------- + ---------- +

3行(0.00秒)