前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Oracle中日期字段未定义日期类型的案例补充说明

Oracle中日期字段未定义日期类型的案例补充说明

作者头像
bisal
发布2022-05-18 13:54:19
1.8K0
发布2022-05-18 13:54:19
举报

Oracle中日期字段未定义日期类型的案例一则》讲到一个用字符串类型的日期字段做分区键的案例,因为这种"不规范"的设计,通过增加一个虚拟列,才实现的日期分区的功能。

原始建表语句,这种不能按照常规的日期数据实现分区,

代码语言:javascript
复制
CREATE TABLE customer(age NUMBER, birthday char(20))
PARTITION BY RANGE (birthday)
(
  PARTITION p1 VALUES less than (to_date('2022-01','yyyy-mm')),
  PARTITION p2 VALUES less than (to_date('2022-02','yyyy-mm')),
  PARTITION p3 VALUES less than (to_date('2022-03','yyyy-mm'))
);

改造成增加一个虚拟列的建表语句,

代码语言:javascript
复制
CREATE TABLE customer(age NUMBER, birthday char(20), partiton_key DATE GENERATED ALWAYS AS (to_date(birthday, 'yyyy-mm-dd')))
PARTITION BY RANGE (partiton_key)
(
  PARTITION p1 VALUES less than (to_date('2022-01','yyyy-mm')),
  PARTITION p2 VALUES less than (to_date('2022-02','yyyy-mm')),
  PARTITION p3 VALUES less than (to_date('2022-03','yyyy-mm'))
);

此时虽然能实现正常的日期分区的功能,但是每次插入INSERT,必须带着除虚拟列外其他的字段,给开发增加了复杂度,

代码语言:javascript
复制
SQL> insert into customer values(1, '2022-01-01');
insert into customer3 values(1, '2022-01-01')
            *
ERROR at line 1:
ORA-00947: not enough values


INSERT INTO customer(age, birthday) values(1, '2022-01-01');

实际上,有时候我们日常的生活中,碰到一个问题,往往可能高估他的难度,或者在潜意识当中认为需要用特殊的方案才可以解决,但实际上,可能最简单的方案就在眼前,这个案例,就是如此。

分区条件直接用字符串,不用to_date(),无论是采用"月",还是"日",

代码语言:javascript
复制
CREATE TABLE customer1(age NUMBER, birthday char(20))
PARTITION BY RANGE (birthday)
(
  PARTITION p1 VALUES less than ('2022-01'),
  PARTITION p2 VALUES less than ('2022-02'),
  PARTITION p3 VALUES less than ('2022-03')
);


CREATE TABLE customer2(age NUMBER, birthday char(20))
PARTITION BY RANGE (birthday)
(
  PARTITION p1 VALUES less than ('2022-01-01'),
  PARTITION p2 VALUES less than ('2022-02-01'),
  PARTITION p3 VALUES less than ('2022-03-01')
);

如下插入语句,都是能执行的,

代码语言:javascript
复制
INSERT INTO customer1 values(1, '2022-01-01');
INSERT INTO customer1 values(1, '2022-02-01');
INSERT INTO customer1 values(2, '2022-02-02');


INSERT INTO customer2 values(1, '2022-01-01');
INSERT INTO customer2 values(1, '2022-02-01');
INSERT INTO customer2 values(2, '2022-02-02');

而且分区数据,都是正确的,这是按照"月"的,

代码语言:javascript
复制
SQL> SELECT * FROM customer1;
       AGE BIRTHDAY
---------- --------------------
         1 2022-01-01
         1 2022-02-01
         2 2022-02-02


SQL> SELECT * FROM customer1 PARTITION(p2);
       AGE BIRTHDAY
---------- --------------------
         1 2022-01-01


SQL> SELECT * FROM customer1 PARTITION(p3);
       AGE BIRTHDAY
---------- --------------------
         1 2022-02-01
         2 2022-02-02

这是按照"天"的,

代码语言:javascript
复制
SQL> SELECT * FROM customer2;
       AGE BIRTHDAY
---------- --------------------
         1 2022-01-01
         1 2022-02-01
         2 2022-02-02


SQL> SELECT * FROM customer2 PARTITION(p2);
       AGE BIRTHDAY
---------- --------------------
         1 2022-01-01


SQL> SELECT * FROM customer2 PARTITION(p3);
       AGE BIRTHDAY
---------- --------------------
         1 2022-02-01
         2 2022-02-02

所以有时候,问题可以先从自身或者最简单的形式考虑,或许就可以得到答案,当然,这还取决于对原理的理解,如果理解到位,可能就脱口而出,否则就会像上面这种,绕道而行,缺练。

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2022-05-17,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档