按男女SQL分组-

时间:2019-03-04 19:37:34

标签: sql oracle

我有一个示例数据库,我试图找到新客户与回头客。下面是我创建的示例数据库的链接:

https://dbfiddle.uk/?rdbms=oracle_11.2&fiddle=aa24ab7ce5136ab99a66efbc5414968f

我想加入两个表,以便获得以下结果:

table picture please have a look

这是我的原始帖子,我只想吸引新老客户:

https://dbfiddle.uk/?rdbms=oracle_11.2&fiddle=e7fbb96a2d269e37d1436e178d523066

逻辑是-我正在尝试从交易表中获取从未交易过的当前客户,作为当前期间的新客户。然后,我要计算当前和过去交易的回头客。现在我想以我附带的图片格式获取数据。基本上将数据分为男性和女性,每个存储桶中的客户数量,总支出,交易数量以及购买数量。

下面是我拥有的代码,但是表中有一条记录不是谁是新客户,但是当我运行此代码时,它使我成为新客户:

    select gender, 
case when age < 18 then '<18'
when age between 18 and 24 then '18-24'
when age between 25 and 32 then '25-32'
when age between 33 and 39 then '35-39'
when age between 40 and 46 then '40-46'
when age between 47 and 53 then '46-52'
when age between 54 and 60 then '53-58'
when age > 60 then '61+' end as AgeGroup
, count(distinct individual_id) indiv
, count (distinct transaction_number) txn_count
, sum(dollar_value_us) as Spend
, sum(quantity),
CASE WHEN MIN(txn_date) = min_txn_date THEN 1 ELSE 0 END is_new
from (SELECT 
        DISTINCT a.individual_id, 
        a.dollar_value_us,
        a.txn_date,
        a.quantity,
        a.transaction_number,
        b.gender,
        b.age,
        MIN(txn_date) OVER(PARTITION BY a.individual_id) min_txn_date          
    FROM transaction_detail_mv   a
    join gender_details b on a.individual_id = b.individual_id
    WHERE 
        a.brand_org_code = 'BRAND'
        AND a.is_merch = 1
        AND a.currency_code = 'USD'
        AND a.line_item_amt_type_cd = 'S')

where txn_date >= TO_DATE('10-02-2019', 'DD-MM-YYYY') 
    AND txn_date < TO_DATE('17-02-2019', 'DD-MM-YYYY')

group by gender, 
case when age < 18 then '<18'
when age between 18 and 24 then '18-24'
when age between 25 and 32 then '25-32'
when age between 33 and 39 then '35-39'
when age between 40 and 46 then '40-46'
when age between 47 and 53 then '46-52'
when age between 54 and 60 then '53-58'
when age > 60 then '61+' end,
individual_id,
min_txn_date

此代码的问题是它没有对年龄范围进行分组。因此,如果有2个年龄段在1岁以下的男性在回头客,那么这给了我两个记录,而我只需要1个。

2 个答案:

答案 0 :(得分:1)

使用PL / SQL过程或匿名PL / SQL块似乎是一种简单可行的选择。使用过多聚合函数的当前查询将来可能会出现性能瓶颈。

  • 根据定义的格式声明一个由整数索引的PL / SQL表 在桌子上。
  • PL / SQL表应具有7(在输出表中定义)+ 1(客户类型-退货/新建)列
  • 通过循环以下结果集有条件地填充表 男性特定的数据元素转到pl / sql表中的相应列,女性特定的数据元素转到每个年龄标准的相应列。
  • 将所有结果集加载到PL / SQL表后,循环 通过以适当格式打印。 希望这会有所帮助。

答案 1 :(得分:1)

提出了使用PL / SQL表的方法来根据表定义(https://i.stack.imgur.com/0cjvm.png)格式化输出。如果那是实际的问题陈述,那么使用PL / SQL将有助于将行转换为列。

关于按年龄组分组和回头客的问题在查询中出现是因为“ individual_id”已添加到group by子句。 Individual_id定义了一个年龄而不是一个年龄组,在group by子句中添加personal_id将创建按“ age”分组的结果集。查询已按如下所示进行了更正,我针对所述情况进行了一些测试,并且可以正常工作。确认是否可行。

select gender, 
case when age < 18 then '<18'
when age between 18 and 24 then '18-24'
when age between 25 and 32 then '25-32'
when age between 33 and 39 then '35-39'
when age between 40 and 46 then '40-46'
when age between 47 and 53 then '46-52'
when age between 54 and 60 then '53-58'
when age > 60 then '61+' end as AgeGroup
, count(distinct individual_id) indiv 
, count (distinct transaction_number) txn_count
, sum(dollar_value_us) as Spend
, sum(quantity),
CASE WHEN MIN(txn_date) = min_txn_date THEN 1 ELSE 0 END is_new
from (SELECT 
        DISTINCT a.individual_id, 
        a.dollar_value_us,
        a.txn_date,
        a.quantity,
        a.transaction_number,
        b.gender,
        b.age,
        MIN(txn_date) OVER(PARTITION BY a.individual_id) min_txn_date          
    FROM transaction_detail_mv   a
    join gender_details b on a.individual_id = b.individual_id
    WHERE 
        a.brand_org_code = 'BRAND'
        AND a.is_merch = 1
        AND a.currency_code = 'USD'
        AND a.line_item_amt_type_cd = 'S')
where txn_date >= TO_DATE('10-02-2019', 'DD-MM-YYYY') 
    AND txn_date < TO_DATE('17-02-2019', 'DD-MM-YYYY')
group by gender, 
case when age < 18 then '<18'
when age between 18 and 24 then '18-24'
when age between 25 and 32 then '25-32'
when age between 33 and 39 then '35-39'
when age between 40 and 46 then '40-46'
when age between 47 and 53 then '46-52'
when age between 54 and 60 then '53-58'
when age > 60 then '61+' end,
/*individual_id,*/
min_txn_date