使用oracle sql生成随机百分比

时间:2017-11-21 07:56:11

标签: sql oracle

我有下表account_ownership:

account    holder
A1         H1
A1         H2
A2         H3
A2         H4
A2         H5
A3         H6
A3         H7
A3         H8
A3         H9

以下是我的需要。

输出:

account    holder   ownership
A1         H1       50
A1         H2       50
A2         H3       50
A2         H4       25
A2         H5       25
A3         H6       60
A3         H7       30
A3         H8       5
A3         H9       5

注意:所有权可以包含介于1到99之间的任何值(无小数部分),但在帐户中最多可以添加100个。

3 个答案:

答案 0 :(得分:1)

试试这个。内联解释了逻辑。

--Dataset

WITH tbl1 (acct, hldr)
     AS (SELECT 'A1', 'H1' FROM DUAL
         UNION ALL
         SELECT 'A1', 'H2' FROM DUAL
         UNION ALL
         SELECT 'A2', 'H3' FROM DUAL
         UNION ALL
         SELECT 'A2', 'H4' FROM DUAL
         UNION ALL
         SELECT 'A2', 'H5' FROM DUAL),
     --dataset end
     -- Counting records for each account
     tbl2 (acct, cnt)
     AS (  SELECT acct, COUNT (1)
             FROM tbl1
         GROUP BY acct),
     -- Counting end
     tbl3 (acct,
           hldr,
           prcnt,
           rnk)
     AS (SELECT tbl1.acct,
                tbl1.hldr,
                ROUND (100 / tbl2.cnt) prcnt,
                DENSE_RANK ()
                OVER (PARTITION BY tbl1.acct ORDER BY tbl1.acct, tbl1.hldr)
                   rnk
           FROM tbl1 INNER JOIN tbl2 ON tbl1.acct = tbl2.acct)
SELECT tbl3.acct,
       tbl3.hldr,
       CASE
          WHEN (rnk = 1) AND MOD (tbl2.cnt, 2) = 1 
           THEN (prcnt + 1)
          ELSE prcnt
       END
  FROM tbl3 
 INNER JOIN tbl2 
 ON tbl3.acct = tbl2.acct
 ORDER BY ACCT;

答案 1 :(得分:1)

WITH tbl1 (acct, hldr)
         AS (SELECT 'A1', 'H1' FROM DUAL
             UNION ALL
             SELECT 'A1', 'H2' FROM DUAL
             UNION ALL
             SELECT 'A2', 'H3' FROM DUAL
             UNION ALL
             SELECT 'A2', 'H4' FROM DUAL
             UNION ALL
             SELECT 'A2', 'H5' FROM DUAL
           )
select acct, hldr,
       case when rn=1 then 100-sum(percent) over(partition by acct)+percent
       else percent end AS percent
  from (
select acct, hldr,
       ceil(dbms_random.value(1,100/count(1) over(partition by acct))) percent,
       row_number() over(partition by acct order by NULL) rn
  from tbl1
)

答案 2 :(得分:1)

使用SQL,如下所示。

WITH account_ownership (account, holder)
             AS (SELECT 'A1', 'H1' FROM DUAL
                 UNION ALL
                 SELECT 'A1', 'H2' FROM DUAL
                 UNION ALL
                 SELECT 'A2', 'H3' FROM DUAL
                 UNION ALL
                 SELECT 'A2', 'H4' FROM DUAL
                 UNION ALL
                 SELECT 'A2', 'H5' FROM DUAL
                 UNION ALL
                 SELECT 'A3', 'H6' FROM DUAL),
        table1 as(
        select a.account,holder,
               sum(1)over(partition by a.account order by holder) as myorder,
               b.mycount,
               dbms_random.value(1,100) myvalue
        from account_ownership a
        left join (select account,count(*) mycount
                   from account_ownership
                   group by account) b
        on a.account = b.account),
        table2 as(
        select a.account,holder,myorder,mycount,trunc(myvalue/sumvalue*100) true_value
        from table1 a
        left join ( select account,sum(myvalue) sumvalue                        from table1
                    group by account) b
        on a.account = b.account)
        select account,holder,case when myorder != mycount then true_value
                                   else 100 - sum_value + true_value end as ownership
        from (select account,holder,myorder,mycount,true_value,
                     sum(true_value) over (partition by account order by myorder) as sum_value
              from table2)