如何添加具有特定值的列并计算百分比?

时间:2017-02-02 13:59:35

标签: sql r oracle percentage

我收到了选择查询这种表格(只是一个简单的例子):

D         C         Letter
20153     200       x
20154     300       x
20161     250       x
20162     180       x
20153     500       y
20154     380       y
20161     550       y
20162     170       y
20153     230       z
20154     700       z
20161     210       z
20162     185       z

因此,列D在四个条目后重复。 C总是不同,并且在四个条目后字母更改。 总计,20153有100.000,20154有150.000,20161有300.000,20162有250.000条目。我想将这些值放到相应的数字,计算百分比,使它看起来像这样:

D         C         Letter    Total      Perc
20153     200       x         100.000    0.002
20154     300       x         150.000    0.002
20161     250       x         300.000    0.008
20162     180       x         250.000    ...
20153     500       y         100.000    ...
20154     380       y         150.000    ...
20161     550       y         300.000    ...
20162     170       y         250.000    ...
20153     230       z         100.000    ...
20154     700       z         150.000    ...
20161     210       z         300.000    ... 
20162     185       z         250.000    ...

我该怎么做? 提供的解决方案也可以用R。

编写

2 个答案:

答案 0 :(得分:0)

这适用于某些数据库

select      D,C,Letter
           ,sum(C) over (partition by D)            as Total
           ,C / sum(C) over (partition by D) * 100  as Perc

from        mytable

如果它对您的数据库不起作用,请尝试以下

select      t.D,t.C,t.Letter
           ,s.Total
           ,t.C / c.Total * 100  as Perc

from        mytable t

            join (select      D,sum(C) as Total 
                  from        mytable
                  group by    D
                  ) s 

            on    s.D = t.D

答案 1 :(得分:0)

您必须在某个地方定义您的给定向量,例如在子查询V中。子查询X会将列RN添加为letter分区并按D排序的行。现在我们可以join这两个查询并进行划分:

with 
  v as (select 1 rn, 100000 as total from dual union all
        select 2 rn, 150000 as total from dual union all
        select 3 rn, 300000 as total from dual union all
        select 4 rn, 250000 as total from dual ),
  x as (select t.*, row_number() over (partition by letter order by d) rn
          from t)
select rn, d, c, letter, total, cast(c / total as number(8, 5)) percent
  from x join v using (rn)
  order by letter, d

测试数据和输出:

create table t (d number(6), c number(6), letter varchar2(2));
insert into t values (20153, 200, 'x');
insert into t values (20154, 300, 'x');
insert into t values (20161, 250, 'x');
insert into t values (20162, 180, 'x');
insert into t values (20153, 500, 'y');
insert into t values (20154, 380, 'y');
insert into t values (20161, 550, 'y');
insert into t values (20162, 170, 'y');
insert into t values (20153, 230, 'z');
insert into t values (20154, 700, 'z');
insert into t values (20161, 210, 'z');
insert into t values (20162, 185, 'z');


    RN       D       C LETTER      TOTAL    PERCENT
 ----- ------- ------- ------ ---------- ----------
     1   20153     200 x          100000    0,00200
     2   20154     300 x          150000    0,00200
     3   20161     250 x          300000    0,00083
     4   20162     180 x          250000    0,00072
     1   20153     500 y          100000    0,00500
     2   20154     380 y          150000    0,00253
     3   20161     550 y          300000    0,00183
     4   20162     170 y          250000    0,00068
     1   20153     230 z          100000    0,00230
     2   20154     700 z          150000    0,00467
     3   20161     210 z          300000    0,00070
     4   20162     185 z          250000    0,00074