Mysql 查询一个报表的两个表(高级)
我在使用高级SQL查询时遇到了一些问题,而且我已经很久没有使用SQL数据库了。我们使用MySQL 背景: 我们将使用两个表: “交易表” 表:历史记录Mysql 查询一个报表的两个表(高级),mysql,sql,join,Mysql,Sql,Join,我在使用高级SQL查询时遇到了一些问题,而且我已经很久没有使用SQL数据库了。我们使用MySQL 背景: 我们将使用两个表: “交易表” 表:历史记录 +---------------+-----------------------------+------+-----+-------------------+-------+ | Field | Type | Null | Key | Default |
+---------------+-----------------------------+------+-----+-------------------+-------+
| Field | Type | Null | Key | Default | Extra |
+---------------+-----------------------------+------+-----+-------------------+-------+
| m_id | int(11) | NO | PRI | 0 | |
| m_a_ordinal | int(11) | NO | PRI | 0 | |
| a_expired_date| datetime | NO | PRI | | |
| a_state | enum('EXPIRED','UNEXPIRED') | YES | | NULL | |
| t_note | text | YES | | NULL | |
| t_updated_by | varchar(40) | NO | | | |
| t_last_update | timestamp | NO | | CURRENT_TIMESTAMP | |
+---------------+-----------------------------+------+-----+-------------------+-------+
“信息表”
表:信息
+---------------------+---------------+------+-----+---------------------+-------+
| Field | Type | Null | Key | Default | Extra |
+---------------------+---------------+------+-----+---------------------+-------+
| m_id | int(11) | NO | PRI | 0 | |
| m_a_ordinal | int(11) | NO | PRI | 0 | |
| a_type | varchar(15) | YES | MUL | NULL | |
| a_class | varchar(15) | YES | MUL | NULL | |
| a_state | varchar(15) | YES | MUL | NULL | |
| a_publish_date | datetime | YES | | NULL | |
| a_expire_date | date | YES | | NULL | |
| a_updated_by | varchar(20) | NO | | | |
| a_last_update | timestamp | NO | | CURRENT_TIMESTAMP | |
+---------------------+---------------+------+-----+---------------------+-------+
我们在一个表中有一组字段来描述记录。每个记录由一个m_id(个人)和一个序号(一个人可以有多个记录)组成。例如,我的m_id可以是1,我可以有多个序数,(1,2,3,4,等等),每个序数都有各自的数据集。m_id和m_a_序数包含“信息”表中的复合键,“事务”表中的m_id、m_a_序数和a_过期日期字段也包含复合键
实际上,当记录过期时,信息表中的a_state字段将更新为expired。同时,在transactions表中创建一条记录,其中包含m_id、m_a_ordinal和a_expired_date。我们发现,在过去,人们会变得不耐烦,可以单击按钮两次,因此,通过之前的一些帮助,我已使用以下查询缩小了每个过期记录的最新交易范围:
SELECT e1.m_id, e1.m_a_ordinal, e1.a_expired_date, e1.t_note, e1.t_updated_by
FROM expire_history e1
INNER JOIN (SELECT m_id, m_a_ordinal, MAX(a_expired_date) AS a_expired_date
FROM expire_history GROUP BY m_id, m_a_ordinal) e2
ON (e2.m_id = e1.m_id AND e2.m_a_ordinal = e1.m_a_ordinal AND e2.a_expired_date = e1.a_expired_date)
WHERE e2.a_expired_date > '2008-05-15 00:00:00' ORDER BY a_date_expired;
看起来很简单,对吧
让我们增加一些复杂性。“信息”表中的每条记录都有一个“自然过期日期”。然而,我们软件的原始开发人员并没有对其进行编码,以在记录达到其自然过期日期后将其状态更改为“过期”。一旦事务过期,它也不会将事务写入事务表(我理解这一点,因为这只是为了保存由个人过期的事务的记录,而不是自动地)。此外,当记录手动过期时,原始过期日期不会更改。这就是为什么它如此复杂:P~~
本质上,我需要构建一个报告来显示过期的所有方面,无论是手动过期还是自然过期
此报告应该从上面的查询中获取数据,并将其与“信息表”上的另一个查询相结合,该查询表示某个日期是否过期
语法可能有点错误,没有时间测试;但你可以从这里得到要点,我希望:
同样,coalesce只返回一系列值中的第一个非空值。如果你只处理两个NULLIF,它也可以工作
语法可能有点错误,没有时间测试;但你可以从这里得到要点,我希望:
同样,coalesce只返回一系列值中的第一个非空值。如果您只处理两个null,则可能也会起作用。Hmm。。我看不出信息表中哪里有“过期”日期。我们少了一张桌子吗?我会计划选择从信息左侧连接到事务过期的事务,然后合并(事务过期日期、项目过期日期)的所有内容。我如何知道“自然过期日期”是什么?或者怎么计算呢?哎呀。很抱歉我删掉了一些不相关的栏目。让我很快更新一下。很抱歉。另外,自然失效日期是出版日期后2年。让我为您插入这两列。关于您的第一个评论,我不能加入到事务过期的位置,因为当事务自然过期时,软件不会将信息表中的状态更改为过期:(…我已经试过了。除非我遗漏了什么。如果你需要一个例子,我可以向你展示特定的查询数据。嗯……我看不出信息表在哪里有“过期”日期。我们在这里遗漏了一个表吗?我会计划选择从信息左连接到事务过期的事务的所有内容,然后合并数据(交易到期日、项目到期日)我如何知道“自然到期日”是什么是吗?或者如何计算?哎呀。对不起。我删掉了一些不相关的栏目。让我很快更新它。对不起。另外,自然过期日期比发布日期晚2年。让我为您插入这两个栏目。关于您的第一条评论,我不能加入他们讨论事务在哪里过期,因为当它过期时,自然软件不会在信息表中将状态更改为“过期”:(…我已经试过了。除非我遗漏了什么。如果您需要示例,我可以向您显示特定的查询数据。很抱歉,响应延迟--我休假了。我如上所述运行了查询,但它返回的行数与刚过期的历史记录上的原始查询相同,因此它不会合并结果(对于自然过期的记录和已终止的记录)。:(对于延迟响应,我感到抱歉——我休假了。我如上所述运行了查询,但它返回的行数与原始查询的just expire_history相同,因此它不会合并结果(指自然过期的记录和已被删除的记录):(
for x in record_total
if (m_id m_a_ordinal) exists in expire_history
display m_id, m_a_ordinal, a_expired_date, a_state)
else if (m_id_a_ordinal) exists in information AND a_expire_date <= CURDATE
display (m_id, m_a_ordinal, a_expire_date, a_state)
end if
x++
SELECT i.m_id, I.m_a_ordinal,
coalesce(e1.a_expired_date, I.A_Expire_Date) as Expire_DT,
coalesce(e1.t_note,'insert related item column'),
coalesce(e1.t_updated_by, I.A_Updated_by) as Updated_By
FROM Information I
LEFT JOIN expire_history e1
ON E1.M_ID = I.M_ID
AND I.m_a_ordinal=e1.M_a_ordinal
INNER JOIN
(SELECT m_id, m_a_ordinal, MAX(a_expired_date) AS a_expired_date
FROM expire_history GROUP BY m_id, m_a_ordinal) e2
ON (e2.m_id = e1.m_id
AND e2.m_a_ordinal = e1.m_a_ordinal
AND e2.a_expired_date = e1.a_expired_date)
WHERE coalesce(e2.a_expired_date,i.A_Expire_Date) > '2008-05-15 00:00:00'
ORDER BY a_date_expired;