Select 值基于联接表中的其他值 SQL
Select values based on other value within joined tables SQL
我想为一个 SQL 请求寻求帮助,该请求给我两个 table 的值。
例如,我有一个 Table 订单和一个 table 处理。
我想报告订单和处理状态。
table orders
id | status | div
-------------------
1 | wating_r | div1
2 | closed | div2
3 | closed | div3
-
table processing:
id | order_id | type | date
----------------------------------------
1 | 2 | send_request | 15.01.15
2 | 2 | send_invoice | 30.01.15
3 | 1 | send_request | 01.02.15
4 | 3 | send_request2 | 10.02.15
5 | 3 | send_invoice | 15.02.15
我想得到什么:
order_id | status | date_request | date_request2 | date_invoice
--------------------------------------------------------------------------------
1 | waiting_r | 01.02.15 | NULL | NULL
2 | closed | 15.01.15 | NULL | 30.01.15
3 | closed | NULL | 10.02.15 | 15.02.15
我的解决方案:
select orders.id as order_id, orders.status, IF(processing.type='send_invoice',date_format(processing.date, '%Y-%m-%d'), NULL) as date_invoice, IF(processing.type='send_request',date_format(processing.date, '%Y-%m-%d'), NULL) as date_request, IF(processing.type='send_request2',date_format(processing.date, '%Y-%m-%d'), NULL) as date_request2
from orders
inner join processing on orders.id = processing.order_id
where
case
when orders.status='closed' then processing.type='send_invoice'
when orders.status='waiting_r' then processing.type='send_request'
when orders.status='waiting_2'then processing.type='send_request2'
end
这工作正常,但使用此 IF 语句我不会成为发送发票时请求的日期 - 我只得到发票的日期。
我尝试了以下而不是案例请求,但在这种情况下,每个订单都有不止一行。当我尝试 "group by" 时,我得到了混合数据。
where
processing.type in ('send_invoice', 'send_request', 'completion_request_send')
您需要将第二个 table 左连接到前三个,就像这样。
SELECT o.id AS order_id, o.status,
p1.date AS date_request,
p2.date AS date_request2,
p3.date AS date_invoice
FROM orders o
LEFT JOIN processing p1 ON o.id = p1.order_id AND p1.type='send_request'
LEFT JOIN processing p2 ON o.id = p2.order_id AND p2.type='send_request2'
LEFT JOIN processing p3 ON o.id = p3.order_id AND p3.type='send_invoice'
ORDER BY 1,2
这个带有 id 匹配标准和特定类型选择的左连接会为每一列提取您需要的行。 Left 与 inner join 不同,它允许缺失值显示为 null。
在这里,工作中。 http://sqlfiddle.com/#!9/b8c74/5/0
这是连接 key/value table 的典型模式,其中 (id/key) 对是唯一的。
Edit 不幸的是,在特定值存在重复键的情况下,它会生成重复的结果集行。为了解决这个问题,在这种情况下,有必要对 key/value table (processing
) 进行重复数据删除。
这个子查询将执行此操作,获取最新的日期值。
SELECT type, order_id, MAX(date) AS date
FROM processing
GROUP BY type, order_id
然后您必须在主查询中使用该子查询。如果 MySQL 有通用的 table 表达式,这会很好。但它并没有让事情变得有点冗长。
SELECT o.id AS order_id, o.status,
p1.date AS date_request,
p2.date AS date_request2,
p3.date AS date_invoice
FROM orders o
LEFT JOIN (
SELECT type, order_id, MAX(date) AS date
FROM processing
GROUP BY type, order_id
) p1 ON o.id = p1.order_id AND p1.type='send_request'
LEFT JOIN (
SELECT type, order_id, MAX(date) AS date
FROM processing
GROUP BY type, order_id
) p2 ON o.id = p2.order_id AND p2.type='send_request2'
LEFT JOIN (
SELECT type, order_id, MAX(date) AS date
FROM processing
GROUP BY type, order_id
) p3 ON o.id = p3.order_id AND p3.type='send_invoice'
ORDER BY 1,2
我想为一个 SQL 请求寻求帮助,该请求给我两个 table 的值。
例如,我有一个 Table 订单和一个 table 处理。
我想报告订单和处理状态。
table orders
id | status | div
-------------------
1 | wating_r | div1
2 | closed | div2
3 | closed | div3
-
table processing:
id | order_id | type | date
----------------------------------------
1 | 2 | send_request | 15.01.15
2 | 2 | send_invoice | 30.01.15
3 | 1 | send_request | 01.02.15
4 | 3 | send_request2 | 10.02.15
5 | 3 | send_invoice | 15.02.15
我想得到什么:
order_id | status | date_request | date_request2 | date_invoice
--------------------------------------------------------------------------------
1 | waiting_r | 01.02.15 | NULL | NULL
2 | closed | 15.01.15 | NULL | 30.01.15
3 | closed | NULL | 10.02.15 | 15.02.15
我的解决方案:
select orders.id as order_id, orders.status, IF(processing.type='send_invoice',date_format(processing.date, '%Y-%m-%d'), NULL) as date_invoice, IF(processing.type='send_request',date_format(processing.date, '%Y-%m-%d'), NULL) as date_request, IF(processing.type='send_request2',date_format(processing.date, '%Y-%m-%d'), NULL) as date_request2
from orders
inner join processing on orders.id = processing.order_id
where
case
when orders.status='closed' then processing.type='send_invoice'
when orders.status='waiting_r' then processing.type='send_request'
when orders.status='waiting_2'then processing.type='send_request2'
end
这工作正常,但使用此 IF 语句我不会成为发送发票时请求的日期 - 我只得到发票的日期。
我尝试了以下而不是案例请求,但在这种情况下,每个订单都有不止一行。当我尝试 "group by" 时,我得到了混合数据。
where
processing.type in ('send_invoice', 'send_request', 'completion_request_send')
您需要将第二个 table 左连接到前三个,就像这样。
SELECT o.id AS order_id, o.status,
p1.date AS date_request,
p2.date AS date_request2,
p3.date AS date_invoice
FROM orders o
LEFT JOIN processing p1 ON o.id = p1.order_id AND p1.type='send_request'
LEFT JOIN processing p2 ON o.id = p2.order_id AND p2.type='send_request2'
LEFT JOIN processing p3 ON o.id = p3.order_id AND p3.type='send_invoice'
ORDER BY 1,2
这个带有 id 匹配标准和特定类型选择的左连接会为每一列提取您需要的行。 Left 与 inner join 不同,它允许缺失值显示为 null。
在这里,工作中。 http://sqlfiddle.com/#!9/b8c74/5/0
这是连接 key/value table 的典型模式,其中 (id/key) 对是唯一的。
Edit 不幸的是,在特定值存在重复键的情况下,它会生成重复的结果集行。为了解决这个问题,在这种情况下,有必要对 key/value table (processing
) 进行重复数据删除。
这个子查询将执行此操作,获取最新的日期值。
SELECT type, order_id, MAX(date) AS date
FROM processing
GROUP BY type, order_id
然后您必须在主查询中使用该子查询。如果 MySQL 有通用的 table 表达式,这会很好。但它并没有让事情变得有点冗长。
SELECT o.id AS order_id, o.status,
p1.date AS date_request,
p2.date AS date_request2,
p3.date AS date_invoice
FROM orders o
LEFT JOIN (
SELECT type, order_id, MAX(date) AS date
FROM processing
GROUP BY type, order_id
) p1 ON o.id = p1.order_id AND p1.type='send_request'
LEFT JOIN (
SELECT type, order_id, MAX(date) AS date
FROM processing
GROUP BY type, order_id
) p2 ON o.id = p2.order_id AND p2.type='send_request2'
LEFT JOIN (
SELECT type, order_id, MAX(date) AS date
FROM processing
GROUP BY type, order_id
) p3 ON o.id = p3.order_id AND p3.type='send_invoice'
ORDER BY 1,2