我在服务器上学习SQL。IBM V7R1M0, DB2.
我正在尝试建立一个SQL报表.在寻找类似的例子几天后,我在知识的海洋中推出了这个瓶...
上下文。商店要求从仓库取货,这些货物是在托盘上拣选的,这些托盘在装车之前会被放在中转车道上。
规则1: 我们只想让一个仓库的托盘放在中转通道上(我们不想把不同仓库的托盘混在一起)。
规则2:店铺会占用附近的暂存通道。
规则3:中转车道按ID排序(有空隙)。
表1.A
|-----|-----|-----------------|
| ID |store|pallet_estimation|
|-----|-----|-----------------|
| 1 | A | 35 |
| 2 | C | 2 |
| 3 | B | 30 |
|-----|-----|-----------------|
SELECT * FROM (
VALUES (1, 'A', 35), (2, 'C', 2), (3, 'B', 30)
) T1(ID, store, pallet_estimation)
表2:
|---------------|---------------|
|ID_staging_lane|pallet_capacity|
|---------------|---------------|
| 201 | 10 |
| 202 | 10 |
| 204 | 30 |
| 205 | 40 |
| 208 | 30 |
| 210 | 30 |
|---------------|---------------|
SELECT * FROM(
VALUES (201, 10), (202, 10), (204, 30), (205, 40), (208, 30), (210, 30)
) T2(ID_staging_lane, pallet_capacity)
预期的结果。
|-----------|--------|--------------------|---------------|------------------|
|T1_sequence|T1_store|T1_pallet_estimation|T2_staging_lane|T2_pallet_capacity|
|-----------|--------|--------------------|---------------|------------------|
| 1 | A | 35 | 201 | 10 |
| 1 | A | 35 | 202 | 10 |
| 1 | A | 35 | 204 | 30 |
| 2 | C | 2 | 205 | 40 |
| 3 | B | 30 | 208 | 30 |
|-----------|--------|--------------------|---------------|------------------|
谢谢你,Charles,谢谢你的时间,我会努力改进我的要求。
如果需要的话,我想把托盘的估计值分成几条栈道,顺序是这样的
例如:
For store A which has 35 pallets,
I want to use staging lane 201 then it remains 35 - 10 = 25 ,
then I want to use staging lane 202 then it remains 25 - 10 = 15,
then I want to use staging lane 204 then it remains 15 - 30 = -15
then I want to continue with the store C on the next staging lane 205 then it remains 2 - 40 = -38
then I want to continue with the store B on the next staging lane 208 then it remains 30 - 30 = 0
你会如何开始建立?- 用窗口函数?SUM() OVER()--用递归SQL ? DECLARE FETCH - 是否可以在SQL中建立一个动态的JOIN?- 其他想法?
先谢谢你。
雷诺
首先,v7r1已经很老了...准确的说是10年了....
第二,我不明白你想加入什么......我看不出有什么可以解释为什么商店A最后在你的结果中出现了3行。
第三,在任何RDBMS中都没有 "动态连接 "这种东西。 你可以有一个dyanmic语句,其中可以包括一个连接。 或者你可以有一个静态语句,其中也可以包含一个连接。 对于IBM i上的Db2来说,只有当你在一个RPGCOLBOL程序或一个SQL存储过程函数中加入语句时才会有关系。
现在说了这么多,让我给你介绍一下通用表表达式(CTE)。 基本上和嵌套表表达式(NTE)是一样的,但我认为更容易理解,而且CTEs在i上也比NTE有性能优势。
with T1 as (
SELECT * FROM (
VALUES (1, 'A', 35), (2, 'C', 2), (3, 'B', 30)
) T1(ID, store, pallet_estimation)
), T2 as (
SELECT * FROM(
VALUES (201, 10), (202, 10), (204, 30), (205, 40), (208, 30), (210, 30)
) T2(ID_staging_lane, pallet_capacity)
), fitment as (
select T1.*, T2.*, row_number() OVER(partition by ID_STAGING_LANE) as rowNbr
from T1 join T2 on pallet_estimation <= pallet_capacity
)
select * from fitment where rowNbr = 1;
嵌套表表达式 with T1 as (<select statement>)
是常用的表格表达式;正如 T2
和 fitment
. 该 with
关键字只用于第一种CTE。
的 fitment
CTE根据车道描述中哪个估计值适合,就把T1和T2合并起来,给每个可能性分配一个行号。 最后的选择是取每个车道的第一个拟合值。
关于CTE的好处是你可以很容易地建立它们,并在你前进的过程中看到结果。 在任何时候您都可以添加 select * from MYCTE
并查看您目前所拥有的内容。
注意,如图所示,一个CTE可以引用另一个CTE。 (fitment
兼顾 T1
和 T2
)
编辑 你需要使用的函数,在结果集中向前或向后查找,这些函数被命名为 LAG()
和 LEAD()
. 它们都属于 OLAP功能 不幸的是,它们是在7.3版本中添加的,你需要使用用户定义函数(UDF)推出自己的版本。
你需要使用一个用户定义的函数(UDF)来推出你自己的版本,这个函数使用了所谓的 "用户定义函数"。scatchpad
来保存每行的函数调用之间的数据。
我发现了一篇很老的文章 在SQL的Scratchpad上涂鸦。 展示如何在RPG中使用刮刮板。 你也可以在一个SQL定义的UDF里面使用它。
做一点google看看你是否可以开始。 如果你遇到问题,请在这里创建一个新问题。 (或者查看 中程邮件列表