满足条件时开始加注,直到SAS中的其他条件
我必须在SAS中解决这个问题。这可能没有那么复杂,但我尝试过使用retain和do循环的方法,但都不起作用 基本上每个ID都有每个日期的数据。根据其他变量,它们可以进入递减状态(变量步长>0),有时它们会满足最终条件1。如果满足条件1=1,我需要标记从减少开始的“事件” 下面是我的数据的示例,我需要的是列标志。我将数据按升序排列,以便我们理解满足条件时开始加注,直到SAS中的其他条件,sas,Sas,我必须在SAS中解决这个问题。这可能没有那么复杂,但我尝试过使用retain和do循环的方法,但都不起作用 基本上每个ID都有每个日期的数据。根据其他变量,它们可以进入递减状态(变量步长>0),有时它们会满足最终条件1。如果满足条件1=1,我需要标记从减少开始的“事件” 下面是我的数据的示例,我需要的是列标志。我将数据按升序排列,以便我们理解 ID date step condition1 flag z 1 0 . z
ID date step condition1 flag
z 1 0 .
z 2 0 .
z 3 0 .
z 4 1 . TRUE
z 5 2 . TRUE
z 6 2 . TRUE
z 7 3 . TRUE
z 8 4 . TRUE
z 10 4 . TRUE
z 11 4 1 TRUE
z 12 4 .
z 13 4 .
z 14 0 .
z 15 0 .
z 16 0 .
z 17 1 .
z 18 2 .
z 19 2 .
z 20 0 .
z 21 0 .
编辑:带有用于确定减少量的变量的表
ID date quantity step condition1 flag
z 1 90 0 .
z 2 90 0 .
z 3 100 0 .
z 4 90 1 . TRUE
z 5 80 2 . TRUE
z 6 80 2 . TRUE
z 7 50 3 . TRUE
z 8 0 4 . TRUE
z 10 0 4 . TRUE
z 11 0 4 1 TRUE
z 12 0 4 .
z 13 0 4 .
z 14 40 0 .
z 15 50 0 .
z 16 60 0 .
z 17 40 1 .
z 18 40 2 .
z 19 30 2 .
z 20 60 0 .
z 21 60 0 .
我试着按ID和降序日期对它进行排序,这似乎是有道理的
proc sort data= have;
by id descending date ;
run;
这是我尝试过的许多事情中的一件——但它被卡住了;(编辑)
需要数据;
集有;
如果四=1,则执行;
do-until(步骤您不能像在数据步骤中那样使用do-until
——它会循环,但不会从输入数据集中读取任何额外的观察值
我认为您需要的关键思想是维护单独的状态变量,以记住您已经看到的内容:
proc sort data=have;
by id date;
run;
data want;
retain episode_started episode_finished;
set have;
by id;
if first.id then do;
episode_started = 0;
episode_finished = 0;
end;
if step > 0 then episode_started = 1;
if episode_started and not episode_finished then flag = 'TRUE';
output;
if condition1 then episode_finished = 1;
run;
我还没有对此进行测试,但应该很接近。您可以查看输出数据集中添加的两个标志,以了解它们的设置时间和方式。您可以通过使用具有两个以上值的单个状态变量来实现相同的目标,但我认为上面的代码更为清晰。在数据集中使用类似的方法之前,您不能使用dotep-它将迭代,但不会从输入数据集中读取任何额外的观察值
我认为您需要的关键思想是维护单独的状态变量,以记住您已经看到的内容:
proc sort data=have;
by id date;
run;
data want;
retain episode_started episode_finished;
set have;
by id;
if first.id then do;
episode_started = 0;
episode_finished = 0;
end;
if step > 0 then episode_started = 1;
if episode_started and not episode_finished then flag = 'TRUE';
output;
if condition1 then episode_finished = 1;
run;
我没有对此进行测试,但应该很接近。您可以查看输出数据集中添加的两个标志,以了解它们的设置时间和方式。您可以通过使用具有两个以上值的单个状态变量来实现相同的目标,但我认为上面的代码更清晰。在需要对se进行评估的组处理中必须应用于相同行的t行可以使用“串行DOW”编码模式完成。您的数据在一个组中可能有多个段,因此整个数据将嵌套在外部do循环中
范例
您的步骤和条件组合约束没有得到充分解释,因此示例逻辑可能无法涵盖所有情况
在本例中,index\u first\u after\u last\u zero
以step>0
跟踪行运行的开始,并以condition1=1
data want;
do until (last.id);
segment = sum(segment,1); * <------ helper for understanding logic;
* 'measuring loop' that computes or tracks some multi-row condition within group;
do index = 1 by 1 until (condition1 or last.id);
set have; * <------ SET inside loop;
by id date; * <------ BY for last.id and ensures dates are ordered;
* track start of last run of non-zero steps;
if step=0 then
index_first_after_last_zero = index + 1;
end;
* track end of run flag;
segment_end_condition = condition1;
* end of loop value is fixed at start of loop and thus not affected by automatic BY 1 increment;
* thus 1 to index iterates same number of rows as the 'measuring' loop;
do index = 1 to index;
set have; * <------ second SET use a separate file buffer than first SET;
* apply flag value -- missing for pre-run rows, and end of run flag to run rows;
if index < index_first_after_last_zero
then flag = .;
else flag = segment_end_condition;
OUTPUT;
end;
end;
run;
需要数据;
直到(最后一个id)为止;
segment=sum(segment,1);*组内处理需要对一组行进行求值,这些行必须应用于同一行,可以使用“串行DOW”编码模式完成。您的数据可能在一个组内有多个段,因此整个过程将嵌套在外部do循环中
范例
您的步骤和条件组合约束没有得到充分解释,因此示例逻辑可能无法涵盖所有情况
在本例中,index\u first\u after\u last\u zero
以step>0
跟踪行运行的开始,并以condition1=1
data want;
do until (last.id);
segment = sum(segment,1); * <------ helper for understanding logic;
* 'measuring loop' that computes or tracks some multi-row condition within group;
do index = 1 by 1 until (condition1 or last.id);
set have; * <------ SET inside loop;
by id date; * <------ BY for last.id and ensures dates are ordered;
* track start of last run of non-zero steps;
if step=0 then
index_first_after_last_zero = index + 1;
end;
* track end of run flag;
segment_end_condition = condition1;
* end of loop value is fixed at start of loop and thus not affected by automatic BY 1 increment;
* thus 1 to index iterates same number of rows as the 'measuring' loop;
do index = 1 to index;
set have; * <------ second SET use a separate file buffer than first SET;
* apply flag value -- missing for pre-run rows, and end of run flag to run rows;
if index < index_first_after_last_zero
then flag = .;
else flag = segment_end_condition;
OUTPUT;
end;
end;
run;
需要数据;
直到(最后一个id)为止;
段=和(段,1)*你知道下降开始的时间吗?前后是否有一组变量可用于确定这是否是下降的开始?如果是,我可能有一个解决方案。你能用测量下降的感兴趣变量更新你的示例数据吗?我在下降开始的地方添加了一列测量。但我不确定它带来的不仅仅是变量步长本身。只有步长=1才能界定递减的开始。谢谢。你知道递减的开始是什么时候吗?前后是否有一组变量可用于确定这是否是递减的开始?如果是,我可能有一个解决方案r你。你能用测量下降的感兴趣的变量更新你的示例数据吗?我已经添加了一个列,其中测量了下降。但我不确定它带来的不仅仅是变量步长本身。只有步长=1才能界定下降的开始。谢谢你Richard,我不认为我能得出w用这个。它工作得很好。谢谢你,Richard,我不认为我能想出这个。它工作得很好。谢谢你的回答,问题是如果减少了,但最后没有满足条件1,这段代码仍然会标记它。也许它可以处理颠倒的数据(按降序日期排序)?谢谢您的回答,问题是如果有减少,但最后没有满足条件1,此代码仍将标记它。也许它可以处理颠倒的数据(按降序日期排序)?