繁体   English   中英

MySQL:对具有相同列的表进行LEFT JOIN

[英]MySQL: LEFT JOIN on tables having same columns

这是3个MySQL表:

CREATE TABLE `t1` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  PRIMARY KEY (`id`)
);


CREATE TABLE `t2` (
  `id` int(11) NOT NULL,
  `a` int(11) NOT NULL,
  `b` int(11) NOT NULL,
  PRIMARY KEY (`id`)
);


CREATE TABLE `t3` (
  `id` int(11) NOT NULL,
  `b` int(11) NOT NULL,
  `c` int(11) NOT NULL,
  PRIMARY KEY (`id`)
);

我想从此表中获取所有数据:

select * from t1
left join t2 on t1.id=t2.id
left join t3 on t1.id=t3.id;

结果是(表中有一些随机数据):

+----+------+------+------+------+------+------+
| id | id   | a    | b    | id   | b    | c    |
+----+------+------+------+------+------+------+
|  1 |    1 |   42 |   42 | NULL | NULL | NULL |
|  2 | NULL | NULL | NULL |    2 |   43 |   43 |
+----+------+------+------+------+------+------+
2 rows in set (0.00 sec)

我正在使用mysqli_result :: fetch_object(PHP)检索和处理数据:

$mysqli = new mysqli('localhost', 'root', '', 'test');

$result = $mysqli->query('select * from t1
    left join t2 on t1.id=t2.id
    left join t3 on t1.id=t3.id;');

var_dump($result->fetch_object());
var_dump($result->fetch_object());

所以我有2个对象,但有些列为null:

object(stdClass)[3]
  public 'id' => null
  public 'a' => string '42' (length=2)
  public 'b' => null
  public 'c' => null
object(stdClass)[3]
  public 'id' => string '2' (length=1)
  public 'a' => null
  public 'b' => string '43' (length=2)
  public 'c' => string '43' (length=2)

我能理解为什么会发生这种情况(某些列具有相同的名称),但是我宁愿只有非空值! 就我而言,我有更多的表和更多的列。 因为我在PHP代码是“盲”我不能用在列的别名:我想用b ,而不是一个别名b

因此,我想在该查询中“首选”非null值(没有其他顺序规则)。

指定字段,并使用coalesce函数获取其中一个的值:

select 
  coalesce(t2.b, t3.b) as b,
  coalesce(t2.c, t3.c) as c
from t1
left join t2 on t1.id=t2.id
left join t3 on t1.id=t3.id;

但是请注意,如果两个“ b”都不为null,则在t2中只能得到一个。 如果两个都为空,则结果仍然为空。

PS:MySQL还具有IFNULL函数。 但是IFNULL只接受两个值,它对于其他数据库的可移植性较差,因此我更喜欢合并自己。

使用->fetch(PDO::FETCH_NUM)代替。 这将获取一个带编号的数组,而不是字符串键,因此您的“重复”字段名不会相互覆盖。 您将在查询结果的每个字段中获得一个数组条目。 但是您必须非常小心地将那些数组条目映射回查询,因为$row[7]正是查询中的哪个字段? 没有办法真正确定。

更好的选择是在查询中为您的字段加上别名,因此它们确实具有唯一的名称:

SELECT t1.a AS t1a, t2.2 AS t2a, etc...

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM