sqlite中出现意外的向后不兼容性

时间:2013-10-17 17:34:32

标签: sqlite

我有一个运行sqlite 3.7.16.2的开发环境和一个运行sqlite 3.7.9的生产环境,我遇到了一些意想不到的向后兼容性。

我有一个看起来像这样的表:

sqlite> select * from calls;
ID|calldate|calltype
1|2013-10-01|monthly
1|2013-11-01|3 month
1|2013-12-01|monthly
2|2013-07-11|monthly
2|2013-08-11|monthly
2|2013-09-11|3 month
2|2013-10-11|monthly
2|2013-11-11|monthly
3|2013-04-22|monthly
3|2013-05-22|monthly
3|2013-06-22|3 month
3|2013-07-22|monthly
4|2013-10-04|monthly
4|2013-11-04|3 month
4|2013-12-04|monthly
5|2013-10-28|monthly
5|2013-11-28|monthly

使用较新版本的sqlite(3.7.16.2),我可以使用:

SELECT ID, MIN(calldate), calltype FROM calls WHERE calldate > date('NOW') GROUP BY ID;

给了我:

ID|MIN(calldate)|calltype
1|2013-11-01|3 month
2|2013-11-11|monthly
4|2013-11-04|3 month
5|2013-10-28|monthly

然而,当我在旧版本的sqlite(3.7.9)上运行相同的代码时,我得到了这个:

ID|MIN(calldate)|calltype
1|2013-11-01|monthly
2|2013-11-11|monthly
4|2013-11-04|monthly
5|2013-10-28|monthly

我查看了更改here,但无法弄清楚为什么还会发生这种情况。有关如何解决此问题或如何重写我的查询的任何建议?

1 个答案:

答案 0 :(得分:0)

您正在使用SQLite 3.7.11中添加的扩展程序。

在标准SQL中,不允许使用既不出现在GROUP BY子句中也不包含在聚合函数中的列。 (SQLite默认接受这一点以与MySQL兼容,但从组中的某些随机记录返回数据。)

要从具有最小值的记录中获取其他列,您必须首先搜索每个组的最小值,然后将这些列与原始表连接:

SELECT calls.ID,
       calls.calldate,
       calls.calltype
FROM calls
JOIN (SELECT ID,
             MIN(calldate) AS calldate
      FROM calls
      WHERE calldate > date('now')
      GROUP BY ID
     ) AS earliest
ON calls.ID       = earliest.ID       AND
   calls.calldate = earliest.calldate