【问题标题】:SAS - how to 'sum up' based on consecutive occurrencesSAS - 如何根据连续出现“总结”
【发布时间】:2018-01-25 07:50:08
【问题描述】:

第一次发帖,希望有人可以帮助解决我在 SAS EG 中面临的这个问题(仍在学习 SAS 编码,所以请善待!)

如果您在下面看到数据集的 sn-p,我正在尝试根据标志为该 Ref 显示的连续出现次数来计算 Ref 的分数 (pts)。

例如: 如果您将 Ref 505 用于 A_Flag,则该标志有 2 组不同的连续出现,则得分如下:

  • 第一个 ID > 第一个实例 = 25 分
  • 第二个 ID > 第二个实例但连续第一个实例 = 双倍至 50 分
  • 第三个 ID > 0 个实例 = 0 分
  • 第 4 个 ID > 第一个实例 = 25 分
  • 第 5 个 ID > 第 2 个实例但第 1 个连续实例 = 双倍至 50 分
  • 第 6 个 ID > 0 个实例 = 0 分

因此,此 Ref A_Pts 将是 150 分。

另一个例子: 如果您将 Ref 527 用于 B_Flag,则该标志连续出现 4 次,因此每个 ID 取芯:

  • 第一个 ID > 0 个实例 = 0 分
  • 第二个 ID > 第一个实例 = 10 分
  • 第 3 个 ID > 第 2 个实例但第 1 个连续实例 = 双倍至 20 分
  • 第 4 个 ID > 第 3 个实例但连续第 2 个实例 = 双倍至 40 分
  • 第 5 个 ID > 第 4 个实例但连续第 3 个实例 = 双倍至 80 分

因此,此 Ref B_Pts 将是 150 分

我不得不说,这些数据符合我想要实现的目标。

我曾尝试使用 LAG 函数,但这仅适用于第一个连续实例。

我也尝试计算一个计数 - 基于猫的枚举变量(Ref,A_Flag) - 但它随后错误地对数据进行排序并且没有相应地计数

希望这对外面的人有意义!

有问题的数据集:

+-----------+-----+--------+--------+--------+-------+-------+
|   date    | Ref | FormID | A_Flag | B_Flag | A_Pts | B_Pts |
+-----------+-----+--------+--------+--------+-------+-------+
| 01-Feb-17 | 505 |  74549 | A      |        |    25 |     0 |
| 01-Feb-17 | 505 |  74550 | A      |        |    25 |     0 |
| 10-Jan-17 | 505 |  82900 |        | B      |     0 |    10 |
| 13-Jan-17 | 505 |  82906 | A      |        |    25 |     0 |
| 09-Jan-17 | 505 |  82907 | A      |        |    25 |     0 |
| 11-Jan-17 | 505 |  82909 |        | B      |     0 |    10 |
| 03-Jan-17 | 527 |  62549 | A      |        |    25 |     0 |
| 04-Jan-17 | 527 |  62550 |        | B      |     0 |    10 |
| 04-Jan-17 | 527 |  76151 |        | B      |     0 |    10 |
| 04-Jan-17 | 527 |  76152 | A      | B      |    25 |    10 |
| 04-Jan-17 | 527 |  76153 | A      | B      |    25 |    10 |
+-----------+-----+--------+--------+--------+-------+-------+

期望的输出(除非有更好的建议):

+-----------+-----+--------+--------+--------+-----------+-----------+
|   date    | Ref | FormID | A_Flag | B_Flag | A_Pts_Agg | B_Pts_Agg |
+-----------+-----+--------+--------+--------+-----------+-----------+
| 01-Feb-17 | 505 |  74549 | A      |        |        25 |         0 |
| 01-Feb-17 | 505 |  74550 | A      |        |        50 |         0 |
| 10-Jan-17 | 505 |  82900 |        | B      |         0 |        10 |
| 13-Jan-17 | 505 |  82906 | A      |        |        25 |         0 |
| 09-Jan-17 | 505 |  82907 | A      |        |        50 |         0 |
| 11-Jan-17 | 505 |  82909 |        | B      |         0 |        10 |
| 03-Jan-17 | 527 |  62549 | A      |        |        25 |         0 |
| 04-Jan-17 | 527 |  62550 |        | B      |         0 |        10 |
| 04-Jan-17 | 527 |  76151 |        | B      |         0 |        20 |
| 04-Jan-17 | 527 |  76152 | A      | B      |        25 |        40 |
| 04-Jan-17 | 527 |  76153 | A      | B      |        50 |        80 |
+-----------+-----+--------+--------+--------+-----------+-----------+

所以加起来就是

+-----+-----------+-----------+
| Ref | A_Pts_Agg | B_Pts_Agg |
+-----+-----------+-----------+
| 505 |       150 |        20 |
| 527 |       100 |       150 |
+-----+-----------+-----------+

【问题讨论】:

  • 请将您尝试生成的相应输出添加到您提供的示例输入数据中。
  • 现在包括输出
  • 您应该能够使用retain 语句和按组处理来执行此操作。如果遇到困难,请尝试发布您的代码。

标签: sas enterprise-guide


【解决方案1】:

试试这个:

data have;
infile cards dlm='|';
input date :date7. Ref :8. FormID :8. A_Flag :$1. B_Flag :$1. A_Pts :8.  B_Pts :8.;
format date date7.;
cards;
| 01-Feb-17 | 505 |  74549 | A      |        |    25 |     0 |
| 01-Feb-17 | 505 |  74550 | A      |        |    25 |     0 |
| 10-Jan-17 | 505 |  82900 |        | B      |     0 |    10 |
| 13-Jan-17 | 505 |  82906 | A      |        |    25 |     0 |
| 09-Jan-17 | 505 |  82907 | A      |        |    25 |     0 |
| 11-Jan-17 | 505 |  82909 |        | B      |     0 |    10 |
| 03-Jan-17 | 527 |  62549 | A      |        |    25 |     0 |
| 04-Jan-17 | 527 |  62550 |        | B      |     0 |    10 |
| 04-Jan-17 | 527 |  76151 |        | B      |     0 |    10 |
| 04-Jan-17 | 527 |  76152 | A      | B      |    25 |    10 |
| 04-Jan-17 | 527 |  76153 | A      | B      |    25 |    10 |
;
run;

data want;
  set have;
  by Ref;
  retain A_pts_agg B_pts_agg;
  if first.Ref then do;
    A_pts_agg = A_pts;
    B_pts_agg = B_pts;
  end;
  if lag(A_flag) ne (A_flag) then A_pts_agg = A_pts;
  else if A_flag = 'A' then A_pts_agg = A_pts_agg * 2;
  if lag(B_flag) ne (B_flag) then B_pts_agg = B_pts;
  else if B_flag = 'B' then B_pts_agg = B_pts_agg * 2;
run;

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2019-11-14
    • 1970-01-01
    • 2022-10-07
    • 2020-06-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多