MySql左外连接不按预期工作

时间:2015-04-11 19:52:56

标签: java mysql hibernate join

我有以下表结构。

贷款和loan_repayment之间的关系是一对多

贷款

---------------------------------------------------------------------------------------
   id   |                 loan_amount         |           loan_duration         
---------------------------------------------------------------------------------------
    1   |                    60000            |                 3               
    2   |                    80000            |                 4
---------------------------------------------------------------------------------------

loan_repayment

---------------------------------------------------------------------------------------
   id   |      loan_id     |      amount      |       month      |       status
---------------------------------------------------------------------------------------
    1   |          1       |       20000      |         1        |       Pending
    2   |          1       |       20000      |         2        |       Pending
    3   |          1       |       20000      |         3        |       Pending


    4   |          2       |       20000      |         1        |       Pending
    5   |          2       |       20000      |         2        |       Pending
    6   |          2       |       20000      |         3        |       Pending
    7   |          2       |       20000      |         4        |       Pending

我想从整个两张表中仅获取每笔贷款的贷款金额及其各自的付费月数。我正在做这样的查询。

SELECT loan.`loan_amount`, COUNT(loan_repayment.`loan_id`) FROM loan 
LEFT OUTER JOIN loan_repayment ON 
      (loan.`id`=loan_repayment.`loan_id` AND loan_repayment.`status`='Paid' ) 
GROUP BY loan_repayment.`loan_id`

我在这里使用左外连接,所以即使loan_repayment表根据where子句为null,我仍然可以得到0的结果。但问题是,它只返回以下数据。我不知道为什么现在它会返回以下(贷款)行。

---------------------------------------------------------------------------------------
             loan_amount                  |        count(loan_repayment.loan_id)
---------------------------------------------------------------------------------------
                60000                     |                     0
---------------------------------------------------------------------------------------

Actully我已经创建了一个包含许多其他限制的Hibernate标准,但是在进一步调查生成的sql之后,它缩小到了这一点。为什么第二行数据及其子数据不包含在建议的sql的结果中?

如果可以在hibernate标准中复制它也会有所帮助(没什么大不了的,我可以弄清楚,但是担心那个sql的结果)。

更新:

如果我从

更改了查询
loan_repayment.`status`='Paid' 

loan_repayment.`status`='Pending'

我得到以下结果

---------------------------------------------------------------------------------------
             loan_amount                  |        count(loan_repayment.loan_id)
---------------------------------------------------------------------------------------
                60000                     |                     3
                80000                     |                     4
---------------------------------------------------------------------------------------

为什么它没有产生相同的结果,并且在完全相反的条件下计数为0,这有点奇怪。

2 个答案:

答案 0 :(得分:1)

看起来只是错误的GROUP BY,请尝试GROUP BY loan.id,如下所示

SELECT loan.`loan_amount`, COUNT(loan_repayment.`loan_id`) FROM loan 
LEFT OUTER JOIN loan_repayment ON 
      (loan.`id`=loan_repayment.`loan_id` AND loan_repayment.`status`='Paid' ) 
GROUP BY loan.id

答案 1 :(得分:1)

在查看之前的问题时,只是面对这个问题而没有接受或赞成的答案。

除了group by子句之外,您的查询是正确的,您已按right side left join GROUP BY loan_repayment.loan_id的{​​{1}}表中的字段进行分组,即&#39 ;为什么你没有其他值,你应该按loan.id对它们进行分组,测试一下:

架构:

create table loan( id int, loan_amount  int, loan_duration int);
insert into loan values
(1,60000,3),(2,80000,4);
create table loan_repayment (id int,loan_id int,amount int,month int,status varchar(20));
insert into loan_repayment values
(1 ,1 ,20000,1,'Pending'),(2 ,1 ,20000,2,'Pending'),(3 ,1 ,20000,3,'Pending'),
(4 ,2 ,20000,1,'Pending'),(5 ,2 ,20000,2,'Pending'),(6 ,2 ,20000,3,'Pending'),
(7 ,2 ,20000,4,'Pending');

现在使用此查询

SELECT l.loan_amount, COUNT(lr.loan_id) as Paied 
FROM loan l
LEFT OUTER JOIN loan_repayment lr ON 
      (l.id=lr.loan_id AND lr.status='paid') 
GROUP BY l.id

你会得到

loan_amount Paied
60000       0
80000       0

您还可以同时拥有paidpending

SELECT l.loan_amount, SUM(CASE 
                            WHEN lr.status='paid' THEN 1
                            ELSE 0
                          END) as Paied,
                       SUM(CASE 
                            WHEN lr.status='Pending' THEN 1
                            ELSE 0
                          END) as Pending

FROM loan l
LEFT OUTER JOIN loan_repayment lr ON 
      (l.id=lr.loan_id) 
GROUP BY l.id

结果:

loan_amount Paied   Pending
60000       0       3
80000       0       4

您可以使用Hibernate HQLCriteria api获得以上结果,我不认为映射上述查询是否太困难(第一个查询是您尝试过的)Hibernate HQL或Criteria。