【问题标题】:Convert a VARCHAR value to a formatted date, ignoring errors将 VARCHAR 值转换为格式化日期,忽略错误
【发布时间】:2020-07-01 08:55:54
【问题描述】:

我有一列包含yyyy-mm-dd 格式的日期。现在我正在运行SELECT 查询,使用TO_CHAR(dob :: DATE, 'dd/mm/yyyy') AS dob 将该日期转换为dd/mm/yyyy,效果很好。现在我遇到的问题是该列中有一些坏记录,下面是一个有好记录和坏记录的示例表:

| id |    dob     |
|----|------------|
|  1 | 2019-12-31 | // this returns 31/12/2019
|  2 | 31-12-2019 | // BAD RECORD, this returns an error
|----|------------|

我在 id 2 上得到的错误是:

ERROR:  date/time field value out of range: "31-12-2019"
HINT:  Perhaps you need a different "datestyle" setting.
SQL state: 22008

我想要有条件地检查TO_CHAR(dob :: DATE, 'dd/mm/yyyy') 是否可以,否则只需使用 dob 而不进行转换。有什么办法可以解决吗?

我正在使用 Postges 12

【问题讨论】:

  • 更大的问题是您在此处将日期存储为文本。您需要清理 bith 列的日期,但 Postgres 不是这样做的最佳场所。
  • 是的,系统的初始设计只需要文本,仅用于显示目的。但后来,添加了一项功能,用户要求从出生日期确定年龄。这是很久以后的事了
  • 您可以定义使用try/catch块的转换函数并在select语句中使用它

标签: postgresql date to-char postgresql-12


【解决方案1】:

我能够通过在@a_horse_with_no_name > update vachar column to date in postgreSQL 发布的链接中创建类似于所选答案的函数来解决此问题。功能:

create or replace function format_date_or_return_string(str varchar)
returns text language plpgsql as $$
begin
    return to_char(to_date(str, 'yyyy-mm-dd), 'dd-mm-yyyy');
exception
    when others then return str;
end $$;

所以SELECT 将根据需要格式化好记录并忽略坏记录。

SELECT id, format_date_or_return_string(dob) 来自问题中的样本数据将返回:

| 1 | 31/12/2019 | // good record
| 2 | 31-12-2019 | // ignored bad record

【讨论】:

    【解决方案2】:

    将日期存储为字符串不是一个好习惯,您的问题证明了这一点。
    如果您确定此列中格式为YYYY-MM-DD 的所有值都是有效日期,则使用运算符LIKE

    CASE 
      WHEN dob LIKE '____-__-__' THEN TO_CHAR(dob::DATE, 'dd/mm/yyyy') 
      ELSE dob
    END AS dob
    

    【讨论】:

      猜你喜欢
      • 2017-07-20
      • 2013-08-13
      • 1970-01-01
      • 2019-10-21
      • 1970-01-01
      • 2020-12-08
      • 2019-01-23
      相关资源
      最近更新 更多