SQLite子查询语法/错误/与MySQL的区别

时间:2010-04-29 20:00:46

标签: sql sqlite subquery

我认为这是有效的SQLite语法:

SELECT
  *,
  (SELECT amount AS target 
     FROM target_money 
    WHERE start_year <= p.bill_year 
      AND start_month <= p.bill_month 
 ORDER BY start_year ASC, start_month ASC 
    LIMIT 1) AS target
FROM payments AS p;

但我想这不是,因为SQLite会返回此错误:

  

没有这样的专栏:p.bill_year

我如何引用p.bill_year有什么问题?
是的,我是肯定的表payments主持一个列bill_year。我疯了还是这只是有效的SQL语法?它会工作在MySQL不会吗?我没有任何其他SQL存在,所以我无法测试其他人,但我认为SQLite非常标准。

3 个答案:

答案 0 :(得分:2)

谢谢,Mark 您的查询在SQLite中工作正常:

>>> import sqlite3
>>> conn = sqlite3.connect(':memory:')
>>> c = conn.cursor()

>>> c.execute('CREATE TABLE payments (bill_year INT, bill_month INT);')
<sqlite3.Cursor object at 0x00C62CE0>
>>> conn.commit()

>>> c.execute("""CREATE TABLE target_money 
        (amount INT, start_year INT, start_month INT);""")
<sqlite3.Cursor object at 0x00C62CE0>
>>> conn.commit()

>>> c.execute("""
... SELECT
...   *,
...   (SELECT amount AS target
...    FROM target_money
...    WHERE start_year <= p.bill_year AND start_month <= p.bill_month
...    ORDER BY start_year ASC, start_month ASC
...    LIMIT 1) AS target
... FROM
...   payments AS p;
... """)
<sqlite3.Cursor object at 0x00C62CE0>
>>> c.fetchall()
[]

答案 1 :(得分:1)

适用于MySQL:

CREATE TABLE payments (bill_year INT, bill_month INT);
CREATE TABLE target_money (amount INT, start_year INT, start_month INT);

SELECT
  *,
  (SELECT amount AS target
   FROM target_money
   WHERE start_year <= p.bill_year AND start_month <= p.bill_month
   ORDER BY start_year ASC, start_month ASC
   LIMIT 1) AS target
FROM
  payments AS p;

我想它也适用于SQLite。我相信这里有人可以复制&amp;粘贴上面的内容来验证它......

答案 2 :(得分:1)

我做了一些测试,以确认相关的子查询不适用于sqlite2,但适用于sqlite3,这似乎是一个案例。问题是官方文件没有说明这一点。在一些奇怪的语法下,sqlite2中支持相关子查询的可能性很小。多数民众赞成在没有进入sqlite2源代码的情况下我可以告诉你。