【问题标题】:Comparing results with today's date?将结果与今天的日期进行比较?
【发布时间】:2012-05-10 20:20:49
【问题描述】:

有没有办法在 SQL 中使用Now() 函数来选择具有今天日期的值?

我的印象是Now() 将包含时间和日期,但今天的日期会将时间设置为00:00:00,因此这永远不会匹配?

【问题讨论】:

标签: sql sql-server current-time


【解决方案1】:

好的,让我们正确地执行此操作。选择与今天匹配的日期,使用索引(如果可用),并显示所有不同的日期/时间类型。

这里的原理在每种情况下都是相同的。我们抓取日期列在最近午夜或之后的行(今天的日期时间为 00:00:00),以及下一个午夜之前(明天的日期时间为 00:00:00,但不包括具有该确切值的任何内容)。

对于纯日期类型,我们可以和今天的日期做一个简单的比较。

为了让事情保持良好和快速,我们明确避免对存储在数据库中的日期进行任何操作(下面所有示例中的 where 子句的 LHS)。这可能会触发全表扫描,因为必须为每次比较计算日期。 (此行为似乎因 DBMS、YMMV 而异)。

MS SQL Server: (SQL Fiddle | db<>fiddle)

首先,使用日期

select * from dates 
where dte = CAST(CURRENT_TIMESTAMP AS DATE)
;

现在是日期时间:

select * from datetimes 
where dtm >= CAST(CURRENT_TIMESTAMP AS DATE)
and dtm < DATEADD(DD, 1, CAST(CURRENT_TIMESTAMP AS DATE))
;

最后是 DATETIME2:

select * from datetimes2
where dtm2 >= CAST(CURRENT_TIMESTAMP AS DATE)
and dtm2 < DATEADD(DD, 1, CAST(CURRENT_TIMESTAMP AS DATE))
;

MySQL: (SQL Fiddle | db<>fiddle)

使用日期:

select * from dates 
where dte = cast(now() as date)
;

使用日期时间:

select * from datetimes 
where dtm >= cast((now()) as date)
and dtm < cast((now() + interval 1 day) as date)
;

PostgreSQL: (SQL Fiddle | db<>fiddle)

使用日期:

select * from dates 
where dte = current_date
;

使用没有时区的 TIMESTAMP:

select * from timestamps
where ts >= 'today'
and ts < 'tomorrow'
;

甲骨文: (SQL Fiddle)

使用日期:

select to_char(dte, 'YYYY-MM-DD HH24:MI:SS') dte
from dates 
where dte >= trunc(current_date)
and dte < trunc(current_date) + 1
;

使用时间戳:

select to_char(ts, 'YYYY-MM-DD HH24:MI:SS') ts
from timestamps
where ts >= trunc(current_date)
and ts < trunc(current_date) + 1
;

SQLite: (SQL Fiddle)

使用日期字符串:

select * from dates 
where dte = (select date('now'))
;

使用日期和时间字符串:

select dtm from datetimes
where dtm >= datetime(date('now'))
and dtm < datetime(date('now', '+1 day'))
;

使用 unix 时间戳:

select datetime(dtm, 'unixepoch', 'localtime') from datetimes
where dtm >= strftime('%s', date('now'))
and dtm < strftime('%s', date('now', '+1 day'))
;

Backup of SQL Fiddle code

【讨论】:

  • 使用CONVERT(VARCHAR 比较日期并不是最好的方法。最好将日期保留为日期(例如 CAST(CURRENT_TIMESTAMP AS DATE)DATEADD(DAY, 0, DATEDIFF(DAY, 0, CURRENT_TIMESTAMP))stackoverflow.com/questions/1177449/…
  • 我其实是在追求SQL server? :)
  • 第一个例子是 SQL Server。快乐查询:)
【解决方案2】:

不确定您到底想要做什么,但听起来GETDATE() 就是您所追求的。 GETDATE() 返回日期时间,但如果您对时间组件不感兴趣,则可以转换为日期。

SELECT  GETDATE()
SELECT  CAST(GETDATE() AS DATE)

【讨论】:

    【解决方案3】:

    只需将日期的时间元素归零即可。例如

    SELECT DATEADD(dd, DATEDIFF(dd, 0, getdate()), 0)
    

    我使用 GetDate 是因为它是一个 MSSQL 函数,正如您所标记的那样,但 Now() 可能是 MySQL 或者您正在使用 ODBC 函数调用,如果您只是将一个替换为另一个,仍然应该可以工作。

    【讨论】:

      【解决方案4】:

      不知道你在问什么!

      然而

      SELECT  GETDATE()
      

      将为您提供当前日期和时间

      SELECT  DATEADD(dd, 0, DATEDIFF(dd, 0, GETDATE()))
      

      将为您提供时间设置为 00:00:00 的日期

      【讨论】:

        【解决方案5】:

        在前面的答案的基础上,请注意重要的一点,您还需要操作您的表格列以确保它不包含 datetime 数据类型的时间片段。

        下面是一个演示上述内容的小示例脚本:

        select getdate()
        --2012-05-01 12:06:51.413
        select cast(getdate() as date)
        --2012-05-01
        
        --we're using sysobjects for the example
        create table test (id int)
        select * from sysobjects where cast(crdate as date) = cast(getdate() as date)
        --resultset contains only objects created today
        drop table test
        

        我希望这会有所帮助。

        编辑:
        在@dwurf 评论(感谢)关于上述示例可能对性能产生的影响之后,我想建议以下内容。 我们在今天午夜(一天的开始)和一天的最后一毫秒(SQL 服务器计数高达 0.997,这就是我减少 3 毫秒的原因)之间创建一个日期范围。通过这种方式,我们避免了操纵左侧并避免了性能影响。

        select getdate()
        --2012-05-01 12:06:51.413
        select dateadd(millisecond, -3, cast(cast(getdate()+1 as date) as datetime))
        --2012-05-01 23:59:59.997
        select cast(getdate() as date)
        --2012-05-01
        
        create table test (id int)
        select * from sysobjects where crdate between cast(getdate() as date) and dateadd(millisecond, -3, cast(cast(getdate()+1 as date) as datetime))
        --resultset contains only objects created today
        drop table test
        

        【讨论】:

        • 并不总是最好的选择。如果您的表中有一百万个日期,这将很快破坏您的执行计划。
        【解决方案6】:

        如果您有一张只存储日期(没有时间)的表格,并且想在“现在”之前获取这些表格,那么您可以这样做:

        SELECT * FROM tbl WHERE DATEDIFF(d, yourdate, GETDATE())=0
        

        这会导致日差为 0 的行(所以今天)。

        【讨论】:

        • 这里的 d 和 yourdate 是什么?
        • @bobthebuilder 这是您的列或变量包含日期
        【解决方案7】:

        SQL Server 中没有本机 Now() 函数,因此您应该使用:

        select GETDATE() --2012-05-01 10:14:13.403
        

        您可以通过以下方式分别获得日、月和年:

        select DAY(getdate())  --1
        select month(getdate())  --5
        select year(getdate()) --2012
        

        如果您使用的是 sql server 2008,则 DATE 日期时间只有日期部分,没有时间:

        select cast (GETDATE() as DATE) --2012-05-01
        

        【讨论】:

        • Now 是一个 ODBC 函数,因此可以在 MSSQL 中使用 select {fn Now()} 调用
        【解决方案8】:

        你可以试试这个sql代码;

           SELECT [column_1], [column_1], ...    
            FROM (your_table)
             where date_format(record_date, '%e%c%Y') = date_format(now(), '%e%c%Y') 
        

        【讨论】:

          【解决方案9】:

          你可以试试:

          WHERE created_date BETWEEN CURRENT_TIMESTAMP-180 AND CURRENT_TIMESTAMP
          

          【讨论】:

            【解决方案10】:

            这对我有用:

            SELECT * FROM table where date(column_date) = curdate()
            

            【讨论】:

            • 这里的 column_date 是属性名吗?
            【解决方案11】:

            对我来说,如果我想与 DrawDate 进行比较,那么有效的查询是:

            CAST(DrawDate AS DATE) = CAST (GETDATE() as DATE)
            

            这是将结果与今天的日期进行比较。

            或整个查询:

            SELECT TOP (1000) *
            FROM test
            where DrawName != 'NULL' and CAST(DrawDate AS DATE) = CAST (GETDATE() as DATE)
            order by id desc
            

            【讨论】:

              猜你喜欢
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              • 2013-04-06
              • 1970-01-01
              • 2014-11-03
              • 1970-01-01
              • 1970-01-01
              • 2019-03-12
              相关资源
              最近更新 更多