Qlikview聚合
Qlikview aggregation
我有一个 table 如下所示。每个日期都有一个产品。我想按产品汇总并结转总数。但是合计限制为0,对于每一天,每一件产品,我要汇总结转汇总。
Date
product
Amount
06/Jan/2021
a
300
05/Jan/2021
a
200
05/Jan/2021
b
500
04/Jan/2021
a
-100
04/Jan/2021
b
1100
03/Jan/2021
a
-500
03/Jan/2021
b
-900
02/Jan/2021
a
200
02/Jan/2021
b
500
01/Jan/2021
a
100
对于最新日期,我希望看到如下输出:
Date
product
total
06/Jan/2021
a
500
06/Jan/2021
b
1600
查看下面的脚本。
我注释了代码以解释每个步骤。
如果重新加载脚本,结果 table 将是:
基本思路是:
- 按产品和日期(升序)排列记录
- 加载已排序的 table 聚合记录(按产品)
- 如果总和为
< 0
则return0,否则继续聚合
- 一旦我们有了聚合,就会找到每个产品的最大日期并标记这些记录。最大日期记录将包含总金额(每个产品)
- 过滤标记的记录并在最后加载它们table
带注释的加载脚本:
RawData:
Load * inline [
Date , product, Amount
06/Jan/2021, a , 300
05/Jan/2021, a , 200
05/Jan/2021, b , 500
04/Jan/2021, a , -100
04/Jan/2021, b , 1100
03/Jan/2021, a , -500
03/Jan/2021, b , -900
02/Jan/2021, a , 200
02/Jan/2021, b , 500
01/Jan/2021, a , 100
];
NoConcatenate
// Order the data by product and date in ascending order
OrderedData:
Load
date(date#(Date, 'DD/MMM/YYYY')) as Date, // convert to date
product,
Amount
Resident
RawData
Order By
product,
Date asc
;
// we dont need RawData table anymore
Drop Table RawData;
// CalculatedAmount calculation/logic:
// * if the current value for product is not equal to the prvious value
// get the current amount. This the case where the producs are "switched"
// * if the sum of the current Amount value + the previous CalculatedAmount value
// is less than 0 then return 0
// * for the rest of the cases - return the aggregated amount - current Amount
// added to the previous CalculatedAmount
CalculatedAmount:
Load
Date,
product,
Amount,
if( product <> peek('product'), Amount,
if( Amount + peek('CalculatedAmount') < 0, 0,
Amount + peek('CalculatedAmount')
)) as CalculatedAmount
Resident
OrderedData
;
// we dont need OrderedData anymore
Drop Table OrderedData;
// use the CalculatedAmount table to find the max date for each product
// these records are containing the total amount for each product
// flag these records with 1 and join the result table back to
// CalculatedAmount table
join (CalculatedAmount)
Load
max(Date) as Date,
product,
1 as isTotalAmount
Resident
CalculatedAmount
Group By
product
;
// the final table - filter CalculatedAmount table to return
// only the records for which isTotalAmount = 1
TotalAmount:
Load
Date,
product,
CalculatedAmount as TotalAmount
Resident
CalculatedAmount
Where
isTotalAmount = 1
;
// we dont need CalculatedAmount table anymore
Drop Table CalculatedAmount;
我有一个 table 如下所示。每个日期都有一个产品。我想按产品汇总并结转总数。但是合计限制为0,对于每一天,每一件产品,我要汇总结转汇总。
Date | product | Amount |
---|---|---|
06/Jan/2021 | a | 300 |
05/Jan/2021 | a | 200 |
05/Jan/2021 | b | 500 |
04/Jan/2021 | a | -100 |
04/Jan/2021 | b | 1100 |
03/Jan/2021 | a | -500 |
03/Jan/2021 | b | -900 |
02/Jan/2021 | a | 200 |
02/Jan/2021 | b | 500 |
01/Jan/2021 | a | 100 |
对于最新日期,我希望看到如下输出:
Date | product | total |
---|---|---|
06/Jan/2021 | a | 500 |
06/Jan/2021 | b | 1600 |
查看下面的脚本。 我注释了代码以解释每个步骤。
如果重新加载脚本,结果 table 将是:
基本思路是:
- 按产品和日期(升序)排列记录
- 加载已排序的 table 聚合记录(按产品)
- 如果总和为
< 0
则return0,否则继续聚合 - 一旦我们有了聚合,就会找到每个产品的最大日期并标记这些记录。最大日期记录将包含总金额(每个产品)
- 过滤标记的记录并在最后加载它们table
带注释的加载脚本:
RawData:
Load * inline [
Date , product, Amount
06/Jan/2021, a , 300
05/Jan/2021, a , 200
05/Jan/2021, b , 500
04/Jan/2021, a , -100
04/Jan/2021, b , 1100
03/Jan/2021, a , -500
03/Jan/2021, b , -900
02/Jan/2021, a , 200
02/Jan/2021, b , 500
01/Jan/2021, a , 100
];
NoConcatenate
// Order the data by product and date in ascending order
OrderedData:
Load
date(date#(Date, 'DD/MMM/YYYY')) as Date, // convert to date
product,
Amount
Resident
RawData
Order By
product,
Date asc
;
// we dont need RawData table anymore
Drop Table RawData;
// CalculatedAmount calculation/logic:
// * if the current value for product is not equal to the prvious value
// get the current amount. This the case where the producs are "switched"
// * if the sum of the current Amount value + the previous CalculatedAmount value
// is less than 0 then return 0
// * for the rest of the cases - return the aggregated amount - current Amount
// added to the previous CalculatedAmount
CalculatedAmount:
Load
Date,
product,
Amount,
if( product <> peek('product'), Amount,
if( Amount + peek('CalculatedAmount') < 0, 0,
Amount + peek('CalculatedAmount')
)) as CalculatedAmount
Resident
OrderedData
;
// we dont need OrderedData anymore
Drop Table OrderedData;
// use the CalculatedAmount table to find the max date for each product
// these records are containing the total amount for each product
// flag these records with 1 and join the result table back to
// CalculatedAmount table
join (CalculatedAmount)
Load
max(Date) as Date,
product,
1 as isTotalAmount
Resident
CalculatedAmount
Group By
product
;
// the final table - filter CalculatedAmount table to return
// only the records for which isTotalAmount = 1
TotalAmount:
Load
Date,
product,
CalculatedAmount as TotalAmount
Resident
CalculatedAmount
Where
isTotalAmount = 1
;
// we dont need CalculatedAmount table anymore
Drop Table CalculatedAmount;