我在表格中有以下值:
| Val1 | | 201900 | | 201910 | | 201920 | | 201930 | | 201901 | | 201911 | | 201921 | | 201931 | | 201902 | | 201912 | | 201922 | | 201932 |
最后一个数字是2019年的级别(0,1,2,..)。第二个最后一个数字是在特定日期有效的标识符。意味着0在201900的3个月内有效,三个月后将添加新值201910。例如,对于级别0和1,在给定时间将有两个不同的活动记录,分别为201900和201901。我想为这两个记录分配相同的序列号。输出应如下所示:
| Val1 | Seq | | 201900 | 1 | | 201910 | 2 | | 201920 | 3 | | 201930 | 4 | | 201901 | 1 | | 201911 | 2 | | 201921 | 3 | | 201931 | 4 | | 201902 | 1 | | 201912 | 2 | | 201922 | 3 | | 201932 | 4 |
我正在使用Snowflake云DW,但是Oracle语法应该可以正常工作。但是Snowflake按顺序没有CurrVal选项。
我正在尝试此方法,但是不起作用:
> (SUBSTRING(Val1,6,1)=0 OR SUBSTRING(Val1,6,1)=1
> OR SUBSTRING(Val1,6,1)=2 OR
> SUBSTRING(Val1,6,1)=3 OR SUBSTRING(Val1,6,1)=4
> OR SUBSTRING(Val1,6,1)=5) THEN (SELECT s.nextval FROM table(getnextval(test_seq)) s)
答案 0 :(得分:1)
像这样?有用的部分是第16-17行。
SQL> with test (val1) as
2 (select 201900 from dual union all
3 select 201910 from dual union all
4 select 201920 from dual union all
5 select 201930 from dual union all
6 select 201901 from dual union all
7 select 201911 from dual union all
8 select 201921 from dual union all
9 select 201931 from dual union all
10 select 201902 from dual union all
11 select 201912 from dual union all
12 select 201922 from dual union all
13 select 201932 from dual
14 )
15 select val1,
16 row_number() over (partition by substr(val1, 1, 4), substr(val1, -1)
17 order by substr(val1, 5, 1)) seq
18 from test;
VAL1 SEQ
---------- ----------
201900 1
201910 2
201920 3
201930 4
201901 1
201911 2
201921 3
201931 4
201902 1
201912 2
201922 3
201932 4
12 rows selected.
SQL>
答案 1 :(得分:1)
如果VAL1列的数据类型为NUMBER,为什么不这样做呢?
offsetY
输出:
with test (val1) as
(select 201900 from dual union all
select 201910 from dual union all
select 201920 from dual union all
select 201930 from dual union all
select 201901 from dual union all
select 201911 from dual union all
select 201921 from dual union all
select 201931 from dual union all
select 201902 from dual union all
select 201912 from dual union all
select 201922 from dual union all
select 201932 from dual)
select val1,
row_number() over (partition by trunc(val1/100), mod(val1, 10)
order by mod(trunc(val1/10), 10)) seq
from test;
更新#1:
您要询问的是OUTER JOIN
。但是,也许您需要LAG
分析功能的功能?我还认为不需要按标识符排序,因为在按年份和级别划分之后,VAL1列值使我们对结果分区进行自然排序。
+--------+-----+
| VAL1 | SEQ |
+--------+-----+
| 201900 | 1 |
| 201910 | 2 |
| 201920 | 3 |
| 201930 | 4 |
| 201901 | 1 |
| 201911 | 2 |
| 201921 | 3 |
| 201931 | 4 |
| 201902 | 1 |
| 201912 | 2 |
| 201922 | 3 |
| 201932 | 4 |
+--------+-----+
输出:
with
test (val1) as
(select 201900 from dual union all
select 201910 from dual union all
select 201920 from dual union all
select 201930 from dual union all
select 201901 from dual union all
select 201911 from dual union all
select 201921 from dual union all
select 201931 from dual union all
select 201902 from dual union all
select 201912 from dual union all
select 201922 from dual union all
select 201932 from dual),
t as
(select
test.*,
row_number() over (partition by trunc(val1/100), mod(val1, 10)
order by val1) as seq
from test)
select
a.*, b.val1 as prev_value
from t a
left outer join t b
on trunc(a.val1/100) = trunc(b.val1/100) and
mod(a.val1, 10) = mod(b.val1, 10) and
a.seq = b.seq + 1
order by trunc(a.val1/100), mod(a.val1, 10), a.val1;
LAG分析功能:
+--------+-----+------------+
| VAL1 | SEQ | PREV_VALUE |
+--------+-----+------------+
| 201900 | 1 | |
| 201910 | 2 | 201900 |
| 201920 | 3 | 201910 |
| 201930 | 4 | 201920 |
| 201901 | 1 | |
| 201911 | 2 | 201901 |
| 201921 | 3 | 201911 |
| 201931 | 4 | 201921 |
| 201902 | 1 | |
| 201912 | 2 | 201902 |
| 201922 | 3 | 201912 |
| 201932 | 4 | 201922 |
+--------+-----+------------+
输出:
with test (val1) as
(select 201900 from dual union all
select 201910 from dual union all
select 201920 from dual union all
select 201930 from dual union all
select 201901 from dual union all
select 201911 from dual union all
select 201921 from dual union all
select 201931 from dual union all
select 201902 from dual union all
select 201912 from dual union all
select 201922 from dual union all
select 201932 from dual)
select val1,
lag(val1) over (partition by trunc(val1/100), mod(val1, 10)
order by val1) as prev_value
from test;
使用db<>fiddle在线进行测试。