【问题标题】:search in a date range在日期范围内搜索
【发布时间】:2018-09-28 23:48:04
【问题描述】:

我真的被困住了。我有一个 db 表,其中列出了已预订时间段的属性。我需要在表格中搜索日期范围。我当前查询的问题是,如果表中列出的日期超出查询的日期范围,则查询不会返回正确的结果。 这是表格的示例propty_availability

id  BeginDate   EndDate     propid
1   2018-10-02  2018-10-10  155855
2   2018-12-15  2018-12-22  159170
3   2018-12-22  2018-12-25  155855
4   2018-12-26  2018-12-29  155855
5   2018-12-05  2018-12-15  155019
6   2018-11-20  2018-11-27  155855
7   2018-12-18  2018-11-27  155655

我的查询是:

从propty_availability中选择propid
            在哪里
                (开始日期介于“2018-12-20”和“2018-12-27”之间)
                        和
                (EndDate BETWEEN '2018-12-20' AND '2018-12-27')

问题是这个查询将返回记录 3 和 6 只是因为预订的日期范围包括查询的完整日期范围。 我在 begindate 和 enddate 之间尝试了 OR 而不是 AND,但这给了我包含 begindate 或 enddate 的记录。表中包含超出查询日期的列之一的任何内容都不会被列出。

如何让查询向我显示介于我的查询日期之间并对应于表中日期的行? 预期结果是列出第 2、3、4、6、7 行,因为每个行的日期都在查询的范围内。 请随意提问,因为我不熟悉如何在这里发布代码和表格..

【问题讨论】:

  • gave me records that either included begindate or enddate. Anything that is in the table that has one of the columns that fall outside of the queried date don't get listed. 这是矛盾的。 OR 应该是这里的解决方案。编辑:第 6 行和第 7 行不在日期之间,第 7 行实际上是相反的。如果 6 和 7 应该是 2019 年,我想我理解你的问题。
  • 对,对不起,7反了,所以忽略它。问题是我尝试了 OR。如果日期超出要求的查询日期,它仍然不起作用。例如,如果一行有 2018-12-19 和 2018-12-28 则不会返回。问题是我需要返回查询日期所在的行。

标签: php mysql date


【解决方案1】:

在这里使用蛮力...

SELECT propid FROM propty_availability
WHERE 
(BeginDate BETWEEN '2018-12-20' AND '2018-12-27' OR BeginDate < '2018-12-20') 
AND 
(EndDate BETWEEN '2018-12-20' AND '2018-12-27' OR EndDate > '2018-12-20')

所以,可能的情况是:

  1. 您的查询在您的月经之前开始,但在月经期间结束
  2. 里面很整齐
  3. 在期间开始,但在之后结束
  4. 完全重叠
  5. 它完全在外面

一点图形帮助:

                 |---------------------|            # Period
              +-----+ +-----+ +-----------+         # 1, 2, 3
              +---------------------------+         # 4
        +-----+                           +-------+ # 5 (x2)


1:    (false OR true) AND (true OR true)  = true
2:    (true OR false) AND (true OR true)  = true
3:    (true OR false) AND (false OR true)  = true
4:    (false OR true) AND (false or true)  = true 
5:    (false OR true) AND (false OR false) = false
5(2): (false o false) AND (false OR false)  = false

逻辑测试(在 php 中)

is_range_in_range(1, '2018-12-17', '2018-12-22');
is_range_in_range(2, '2018-12-22', '2018-12-25');   
is_range_in_range(3, '2018-12-23', '2018-12-30');   
is_range_in_range(4, '2018-12-17', '2018-12-30');
is_range_in_range(5, '2018-12-01', '2018-12-15');   
is_range_in_range(5, '2018-12-29', '2018-12-31');       
is_range_in_range(6, '2018-11-18', '2018-11-27');

function is_range_in_range($c, $b, $e) {
    $bDate = DateTime::createFromFormat('Y-m-d', '2018-12-20');
    $eDate = DateTime::createFromFormat('Y-m-d', '2018-12-27');

    $b = DateTime::createFromFormat('Y-m-d', $e);
    $e = DateTime::createFromFormat('Y-m-d', $e);

    echo $c . " " . ((($b >= $bDate && $b <= $eDate) || ($b  < $bDate)) 
    && (($e >= $bDate && $e <= $eDate) || ($e > $bDate)) ? 'true' : 'false') . "\n";
}

请注意,endDate &gt; beginDatePeriod 不是拼写错误。

输出:

1 true
2 true
3 true
4 true
5 false
5 false
6 false

【讨论】:

  • 没有尝试过,但我不知道它是否可以工作,因为我也不希望结果超出查询的日期范围。这不会返回一个结果,它会给出所有分别小于或大于开始日期和结束日期的行吗?
  • @you1ca 我认为它很可靠,但谁知道...只有一种方法可以确定。这是六个测试用例...我会尽快回复您...
  • 不,抱歉,它不起作用。现在它给了我零个结果!
  • 几乎...我认为现在的问题是它返回范围之外的所有日期。需要将搜索限制为仅包含截至日期但在范围内的结果。我不知道这是否会让人感到困惑......那列为 8 2018-11-18 2018-11-27 155655 的行呢?这行会出现。但实际上它不应该因为它不在查询范围内,尽管您的查询确实如此,因为从技术上讲 startdate 小于查询日期。有什么办法限制吗?
  • @you1ca 使用您的值 (2018-11-18 2018-11-27) 运行测试并返回 false。您可能需要像我在 php 中那样对运算符进行分组?告诉我,我会更新答案。
猜你喜欢
  • 2017-10-25
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多