while子句中的SQLite count(*)

时间:2014-11-10 16:32:41

标签: sqlite count calendar

我有一个日历表,其中包含未来的所有日期和工作日字段:

fld_date / fld_workday
2014-01-01 / 1
2014-01-02 / 1
2014-01-03 / 0
...

我想选择一个与另一个日期相距n个工作日的日期。我尝试了两种方法,但我失败了:

2014-11-07的第5个工作日:

1

SELECT n1.fld_date FROM calendar as n1 WHERE n1.fld_workday=1 AND  
(select count(*) FROM calendar as n2 WHERE n2.fld_date>='2014-11-07' AND n2.fld_workday=1)=5

它回了0行。

2

SELECT fld_date FROM calendar WHERE fld_date>='2014-11-07' AND fld_workday=1 LIMIT 1  OFFSET 5

没关系,但我想将5天常数更改为字段,而且它不能(它会在更大的选择语句中):

SELECT fld_date FROM calendar WHERE fld_date>='2014-11-07' AND fld_workday=1 LIMIT 1  OFFSET fld_another_field

有什么建议吗?

1 个答案:

答案 0 :(得分:0)

在第一个查询中,子查询不引用n1中的行。

您需要一个相关的子查询:

SELECT fld_Date
FROM Calendar AS n1
WHERE fld_WorkDay = 1
  AND (SELECT COUNT(*)
       FROM Calendar AS n2
       WHERE fld_Date BETWEEN '2014-11-07' AND n1.fld_Date
         AND fld_WorkDay = 1
      ) = 5
LIMIT 1

如果fld_Date列上没有索引,则子查询效率极低。

您可以通过添加另一个估计结果日期的条件来避免为n1中的每一行执行子查询(假设每周大约有四到五个工作日,并且使用额外的几天可以肯定):

...
WHERE fldDate BETWEEN date('2014-11-07', (5 * 4/7 - 10) || ' days')
                  AND date('2014-11-07', (5 * 5/7 + 10) || ' days')
  AND fldWorkDay = 1
  AND (SELECT ...