在雪花中设置变量
Setting variables in snowflake
我想在 CTE table 之前和 CTE table 之后定义变量,因为一些变量取决于 CTE table 的结果。例如
SET(K,B) = (5,2);
with my_data(Key,Index,Value) as (
-- data table as cte
select * from values
(1, 3, 10),
(1, 5, 18),
(1, 14, 4),
(2, 2, 11),
(2, 13, 24),
(2, 29, 40)
)
SELECT VALUE + $K
FROM my_data
这个例子完美运行。但是这段代码:
SET(K,B) = (5,2);
with my_data(Key,Index,Value) as (
-- data table as cte
select * from values
(1, 3, 10 ),
(1, 5, 18 ),
(1, 14, 4 ),
(2, 2, 11 ),
(2, 13, 24),
(2, 29, 40)
)
SET AVG_VAL = (SELECT AVG(VALUE) FROM my_data);
SELECT VALUE + $AVG_VAL
FROM my_data
不是因为雪花给我这个错误
"SQL compilation error: syntax error line 34 at position 0 unexpected 'SET'."
我是否应该创建一个临时 table 来存储此查询 (SELECT AVG(VALUE) FROM my_data)
的结果,然后 include/use 这个临时 table 用于将来的查询而不是变量?
这可以像 -
那样完成
select * from d2;
+-----+-----+
| ID1 | ID2 |
|-----+-----|
| 1 | 2 |
| 100 | 2 |
| 3 | 4 |
| 300 | 4 |
+-----+-----+
设置变量-
set (var1) = (select sum(id2) from d2);
+----------------------------------+
| status |
|----------------------------------|
| Statement executed successfully. |
+----------------------------------+
使用变量-
select id1+$var1 from d2;
+-----------+
| ID1+$VAR1 |
|-----------|
| 13 |
| 112 |
| 15 |
| 312 |
+-----------+
您的“CTE”不是一个独立的“事物”,它仅存在于 SELECT.
的上下文中
因此
WITH cte_x AS (...)
SELECT * FROM cte_x
是一个 SELECT 附加了 CTE。
因此对于您的变量赋值,CTE 必须“在”paren 的
with my_data(Key,Index,Value) as (
select * from values
(1, 3, 10 ),
(1, 5, 18 ),
(1, 14, 4 ),
(2, 2, 11 ),
(2, 13, 24),
(2, 29, 40)
)
SELECT AVG(VALUE) FROM my_data;
AVG(VALUE)
17.833333
鉴于它是 SQL 的离散块,可以将其捕获到变量中:
set AVG_VAL = (
with my_data(Key,Index,Value) as (
select * from values
(1, 3, 10 ),
(1, 5, 18 ),
(1, 14, 4 ),
(2, 2, 11 ),
(2, 13, 24),
(2, 29, 40)
)
SELECT AVG(VALUE) FROM my_data
);
status
Statement executed successfully.
现在我们可以使用该值:
select $AVG_VAL * 2;
$AVG_VAL * 2
35.666666
但是下一个查询:
SELECT VALUE + $AVG_VAL
FROM my_data
002003 (42S02): SQL compilation error:
Object 'MY_DATA' does not exist or not authorized.
没有名为 my_data
的 CTE,因此需要插入:
with my_data(Key,Index,Value) as (
select * from values
(1, 3, 10 ),
(1, 5, 18 ),
(1, 14, 4 ),
(2, 2, 11 ),
(2, 13, 24),
(2, 29, 40)
)
SELECT VALUE + $AVG_VAL
FROM my_data
如果你想要一个可以“使用两次”的 table,你将需要一个实际的 table,此时我建议使用一个临时的 table,这样它只有上下文在这个 session.
Pankaj 回答的性质(通过永久或临时的以太币 table)
另一种方法是简单地使用 windowed AVG 函数:
with my_data(Key,Index,Value) as (
-- data table as cte
select * from values
(1, 3, 10),
(1, 5, 18),
(1, 14, 4),
(2, 2, 11),
(2, 13, 24),
(2, 29, 40)
)
SELECT VALUE, AVG(VALUE) OVER(),
VALUE + AVG(VALUE) OVER()
FROM my_data;
输出:
OVER()
表示 window 用于计算所有行的平均跨度。
我想在 CTE table 之前和 CTE table 之后定义变量,因为一些变量取决于 CTE table 的结果。例如
SET(K,B) = (5,2);
with my_data(Key,Index,Value) as (
-- data table as cte
select * from values
(1, 3, 10),
(1, 5, 18),
(1, 14, 4),
(2, 2, 11),
(2, 13, 24),
(2, 29, 40)
)
SELECT VALUE + $K
FROM my_data
这个例子完美运行。但是这段代码:
SET(K,B) = (5,2);
with my_data(Key,Index,Value) as (
-- data table as cte
select * from values
(1, 3, 10 ),
(1, 5, 18 ),
(1, 14, 4 ),
(2, 2, 11 ),
(2, 13, 24),
(2, 29, 40)
)
SET AVG_VAL = (SELECT AVG(VALUE) FROM my_data);
SELECT VALUE + $AVG_VAL
FROM my_data
不是因为雪花给我这个错误
"SQL compilation error: syntax error line 34 at position 0 unexpected 'SET'."
我是否应该创建一个临时 table 来存储此查询 (SELECT AVG(VALUE) FROM my_data)
的结果,然后 include/use 这个临时 table 用于将来的查询而不是变量?
这可以像 -
那样完成select * from d2;
+-----+-----+
| ID1 | ID2 |
|-----+-----|
| 1 | 2 |
| 100 | 2 |
| 3 | 4 |
| 300 | 4 |
+-----+-----+
设置变量-
set (var1) = (select sum(id2) from d2);
+----------------------------------+
| status |
|----------------------------------|
| Statement executed successfully. |
+----------------------------------+
使用变量-
select id1+$var1 from d2;
+-----------+
| ID1+$VAR1 |
|-----------|
| 13 |
| 112 |
| 15 |
| 312 |
+-----------+
您的“CTE”不是一个独立的“事物”,它仅存在于 SELECT.
的上下文中因此
WITH cte_x AS (...)
SELECT * FROM cte_x
是一个 SELECT 附加了 CTE。
因此对于您的变量赋值,CTE 必须“在”paren 的
with my_data(Key,Index,Value) as (
select * from values
(1, 3, 10 ),
(1, 5, 18 ),
(1, 14, 4 ),
(2, 2, 11 ),
(2, 13, 24),
(2, 29, 40)
)
SELECT AVG(VALUE) FROM my_data;
AVG(VALUE) |
---|
17.833333 |
鉴于它是 SQL 的离散块,可以将其捕获到变量中:
set AVG_VAL = (
with my_data(Key,Index,Value) as (
select * from values
(1, 3, 10 ),
(1, 5, 18 ),
(1, 14, 4 ),
(2, 2, 11 ),
(2, 13, 24),
(2, 29, 40)
)
SELECT AVG(VALUE) FROM my_data
);
status |
---|
Statement executed successfully. |
现在我们可以使用该值:
select $AVG_VAL * 2;
$AVG_VAL * 2 |
---|
35.666666 |
但是下一个查询:
SELECT VALUE + $AVG_VAL
FROM my_data
002003 (42S02): SQL compilation error:
Object 'MY_DATA' does not exist or not authorized.
没有名为 my_data
的 CTE,因此需要插入:
with my_data(Key,Index,Value) as (
select * from values
(1, 3, 10 ),
(1, 5, 18 ),
(1, 14, 4 ),
(2, 2, 11 ),
(2, 13, 24),
(2, 29, 40)
)
SELECT VALUE + $AVG_VAL
FROM my_data
如果你想要一个可以“使用两次”的 table,你将需要一个实际的 table,此时我建议使用一个临时的 table,这样它只有上下文在这个 session.
Pankaj 回答的性质(通过永久或临时的以太币 table)
另一种方法是简单地使用 windowed AVG 函数:
with my_data(Key,Index,Value) as (
-- data table as cte
select * from values
(1, 3, 10),
(1, 5, 18),
(1, 14, 4),
(2, 2, 11),
(2, 13, 24),
(2, 29, 40)
)
SELECT VALUE, AVG(VALUE) OVER(),
VALUE + AVG(VALUE) OVER()
FROM my_data;
输出:
OVER()
表示 window 用于计算所有行的平均跨度。