如何在记录之间分配值

发布于 2024-11-05 03:14:45 字数 684 浏览 0 评论 0原文

我有值 1000 和表:

table
(
  Id int (PK),
  Percent float,
  Value int
)

我必须根据两条法则(两个单独的策略)为该表中的每个记录分配 1000 字段值:

1) 均等分配策略

2) 分配策略的 %

按策略输入 1)

Id  Percent Value
1,  -       0
2,  -       0
3,  -       0

输出

Id  Percent Value
1,  -       333
2,  -       333
3,  -       334

策略输入2)

 Id  Percent Value
 1,  10%       0
 2,  90%       0

输出

Id  Percent Value
1,  10%       100
2,  90%       900

任何人都可以解释一种优雅的方法来做到这一点。 谢谢。

I have value 1000 and table:

table
(
  Id int (PK),
  Percent float,
  Value int
)

I have to distribute 1000 for every record in this table for field Value according to two law (two separated strategy):

1) equal distribution strategy

2) % of distribution strategy

Input by strategy 1)

Id  Percent Value
1,  -       0
2,  -       0
3,  -       0

Output

Id  Percent Value
1,  -       333
2,  -       333
3,  -       334

Input by strategy 2)

 Id  Percent Value
 1,  10%       0
 2,  90%       0

Output

Id  Percent Value
1,  10%       100
2,  90%       900

Could anyone explain an elegant way to do this.
Thank you.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

念三年u 2024-11-12 03:14:45
UPDATE yourtable SET Value =( SELECT 1000/COUNT(Value) from yourtable )

UPDATE yourtable SET Value =( Value * Percent )

但不确定如何处理舍入错误。

编辑:也许在第一种情况下,第二个语句将缺失的数字添加到最后一行。

UPDATE yourtable SET Value = Value + 1000 -( SELECT SUM(Value) from yourtable) where id= (SELECT MAX(Id) from yourtable)

但这并不好,因为最后一行最终可能会出现一个更大的数字……您最终会得到比其余行大得多的数字。 (尝试运行具有 6 个输入行的查询...)

UPDATE yourtable SET Value =( SELECT 1000/COUNT(Value) from yourtable )

UPDATE yourtable SET Value =( Value * Percent )

Not sure how to handle rounding errors, though.

edit: maybe in the first case with a second statement that adds the missing numbers to the last row.

UPDATE yourtable SET Value = Value + 1000 -( SELECT SUM(Value) from yourtable) where id= (SELECT MAX(Id) from yourtable)

But this isn't good, since the last row can end up with a much bigger number... you will end up with a significantly larger number than the rest. (try running the query with 6 input rows...)

夕嗳→ 2024-11-12 03:14:45
DECLARE @valueToDistribute float;
SET @valueToDistribute = 100;

DECLARE @rest int;
DECLARE @temp int;
SET @temp = 0;
DECLARE @error float
SET @error = 0;

DECLARE @tableToDistribute table
(
    id                  int
    ,MaxValue           int 
    ,InitialValue       int 
    ,DistributedValue   int
);

INSERT @tableToDistribute values(1, 0, 0, 0);
INSERT @tableToDistribute values(2, 0, 0, 0);

INSERT @tableToDistribute values(3, 0, 0, 0);
INSERT @tableToDistribute values(4, 0, 0, 0);
INSERT @tableToDistribute values(5, 0, 0, 0);
INSERT @tableToDistribute values(6, 0, 0, 0);
--INSERT @tableToDistribute values(7, 0, 0, 0);
--INSERT @tableToDistribute values(8, 0, 0, 0);
--INSERT @tableToDistribute values(9, 0, 0, 0);


SET   @rest = @valueToDistribute;

WITH Count_CTE (Id, [Percent], MaxId)
AS
(
   SELECT 
          Id
        , [Percent] = CAST(@valueToDistribute / (SELECT COUNT(*) FROM @tableToDistribute) / 100.00 as float)
        , [MaxId] = (SELECT MAX(Id) FROM @tableToDistribute)
    FROM @tableToDistribute
)
UPDATE t 
    SET
       @error = @error + (cte.[Percent] * @valueToDistribute) - ROUND(cte.[Percent] * @valueToDistribute, 0)
      ,@temp = 
        case
            when ROUND(@error, 5) <> 0.00000
                then 
                    case 
                        when t.Id = cte.MaxId then @rest --ROUND(cte.[Percent] * @valueToDistribute, 0) + FLOOR(@error)
                        else ROUND(cte.[Percent] * @valueToDistribute, 0)
                    end 
            else  ROUND(cte.[Percent] * @valueToDistribute, 0)      
        end 
      ,DistributedValue = @temp
      ,@rest = @rest - @temp
FROM @tableToDistribute t 
    inner join Count_CTE cte on t.Id = cte.Id;


SELECT
*
FROM @tableToDistribute
DECLARE @valueToDistribute float;
SET @valueToDistribute = 100;

DECLARE @rest int;
DECLARE @temp int;
SET @temp = 0;
DECLARE @error float
SET @error = 0;

DECLARE @tableToDistribute table
(
    id                  int
    ,MaxValue           int 
    ,InitialValue       int 
    ,DistributedValue   int
);

INSERT @tableToDistribute values(1, 0, 0, 0);
INSERT @tableToDistribute values(2, 0, 0, 0);

INSERT @tableToDistribute values(3, 0, 0, 0);
INSERT @tableToDistribute values(4, 0, 0, 0);
INSERT @tableToDistribute values(5, 0, 0, 0);
INSERT @tableToDistribute values(6, 0, 0, 0);
--INSERT @tableToDistribute values(7, 0, 0, 0);
--INSERT @tableToDistribute values(8, 0, 0, 0);
--INSERT @tableToDistribute values(9, 0, 0, 0);


SET   @rest = @valueToDistribute;

WITH Count_CTE (Id, [Percent], MaxId)
AS
(
   SELECT 
          Id
        , [Percent] = CAST(@valueToDistribute / (SELECT COUNT(*) FROM @tableToDistribute) / 100.00 as float)
        , [MaxId] = (SELECT MAX(Id) FROM @tableToDistribute)
    FROM @tableToDistribute
)
UPDATE t 
    SET
       @error = @error + (cte.[Percent] * @valueToDistribute) - ROUND(cte.[Percent] * @valueToDistribute, 0)
      ,@temp = 
        case
            when ROUND(@error, 5) <> 0.00000
                then 
                    case 
                        when t.Id = cte.MaxId then @rest --ROUND(cte.[Percent] * @valueToDistribute, 0) + FLOOR(@error)
                        else ROUND(cte.[Percent] * @valueToDistribute, 0)
                    end 
            else  ROUND(cte.[Percent] * @valueToDistribute, 0)      
        end 
      ,DistributedValue = @temp
      ,@rest = @rest - @temp
FROM @tableToDistribute t 
    inner join Count_CTE cte on t.Id = cte.Id;


SELECT
*
FROM @tableToDistribute
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文