SAS 将结果输出到输入数据集(相同的输入和输出数据集名称)
SAS outputting results to the input dataset (same in and out dataset name)
我找不到有关此问题的信息,或者无法正确指定问题。
我用代码提问:
这是操作吗
data work.tmp;
set work.tmp;
* some changes to data here;
run;
或者特别是
proc sort data = work.tmp out = work.tmp;
by x;
run;
在任何方面都是危险的,或者在 SAS 中被认为是一种不好的做法?注意相同的输入和输出数据集名称,这是我的要点。 SAS 是否正确处理了这种情况,所以 运行 这种数据 step/procedure?
不会有歧义的结果
后者进行自我分类的频率相当高;因为排序只是重新排列数据集,并且(除非您依赖于其他顺序,或者除非您使用 where
子句来过滤数据集或 rename/keep/drop 选项)不执行任何操作对数据集造成永久性伤害,这不被认为是不好的做法,只要 tmp
正在工作(或打算用作工作目录的 libname)。 SAS 创建一个临时文件来进行排序,当它成功时,它会删除旧文件并重命名临时文件;没有实质性的腐败风险。
前者在数据步骤中将数据集设置为自身,通常不被认为是一种好的做法。那是因为一个数据步骤通常会做一些不可逆的事情——也就是说,如果你运行它一次和你再次运行它有不同的结果。因此,您可能不知道数据集的状态;虽然使用 sort 你可以依靠知道,因为如果它在大多数时间没有正确排序,你会得到一个明显的错误,而数据步骤你可能永远不知道。因此,每个数据步骤通常应该产生一个新的数据集(至少,对那个线程来说是新的)。有时有必要这样做,或者至少不这样做会造成很大的浪费——也许一个宏有时会执行很长的数据步,有时却不会——但通常你可以围绕它进行编程。
虽然文件系统会变得混乱,但这并不危险;类似于sort
,SAS会简单地创建一个临时文件,填充新的数据集,然后删除旧的并重命名临时文件。
(我不提像 modify
这样的事情 必须 为自己设置一个数据集,因为它有一个明显的答案......)
为什么不认为这是好的做法的一些例子。假设您正在交互式工作,并且您有以下名为 tmp
:
的代码数据集
data tmp;
set sashelp.class;
run;
如果您 运行 下面的代码两次,第一次 运行 没问题,但第二次 运行 您会收到警告,因为变量 age no该数据集上不再存在:
data tmp;
set tmp;
drop age;
run;
在这种情况下,这是一个非常无害的示例,您很幸运,SAS 只是发出警告。根据数据步骤的不同,它可能很容易产生错误,例如:
data tmp;
set tmp (rename=(age=blah));
run;
或者更糟的是,它可能不会生成任何错误或警告,并且会像下面的代码那样更改预期结果:
data tmp;
set tmp;
weight = log(weight);
run;
我们的目的是对权重变量应用简单的对数转换以准备建模,但如果我们不小心 运行 第二次执行该步骤,我们将计算 log(log(weight))。不会给出任何警告或错误,并且查看数据集不会立即明显看出任何错误。
IMO,你最好创建迭代数据集,即。 tmp1、tmp2、tmp3 等等...对于以某种方式更新数据集的每个进程。 Space 比花时间调试便宜多了。
我找不到有关此问题的信息,或者无法正确指定问题。
我用代码提问:
这是操作吗
data work.tmp;
set work.tmp;
* some changes to data here;
run;
或者特别是
proc sort data = work.tmp out = work.tmp;
by x;
run;
在任何方面都是危险的,或者在 SAS 中被认为是一种不好的做法?注意相同的输入和输出数据集名称,这是我的要点。 SAS 是否正确处理了这种情况,所以 运行 这种数据 step/procedure?
不会有歧义的结果后者进行自我分类的频率相当高;因为排序只是重新排列数据集,并且(除非您依赖于其他顺序,或者除非您使用 where
子句来过滤数据集或 rename/keep/drop 选项)不执行任何操作对数据集造成永久性伤害,这不被认为是不好的做法,只要 tmp
正在工作(或打算用作工作目录的 libname)。 SAS 创建一个临时文件来进行排序,当它成功时,它会删除旧文件并重命名临时文件;没有实质性的腐败风险。
前者在数据步骤中将数据集设置为自身,通常不被认为是一种好的做法。那是因为一个数据步骤通常会做一些不可逆的事情——也就是说,如果你运行它一次和你再次运行它有不同的结果。因此,您可能不知道数据集的状态;虽然使用 sort 你可以依靠知道,因为如果它在大多数时间没有正确排序,你会得到一个明显的错误,而数据步骤你可能永远不知道。因此,每个数据步骤通常应该产生一个新的数据集(至少,对那个线程来说是新的)。有时有必要这样做,或者至少不这样做会造成很大的浪费——也许一个宏有时会执行很长的数据步,有时却不会——但通常你可以围绕它进行编程。
虽然文件系统会变得混乱,但这并不危险;类似于sort
,SAS会简单地创建一个临时文件,填充新的数据集,然后删除旧的并重命名临时文件。
(我不提像 modify
这样的事情 必须 为自己设置一个数据集,因为它有一个明显的答案......)
为什么不认为这是好的做法的一些例子。假设您正在交互式工作,并且您有以下名为 tmp
:
data tmp;
set sashelp.class;
run;
如果您 运行 下面的代码两次,第一次 运行 没问题,但第二次 运行 您会收到警告,因为变量 age no该数据集上不再存在:
data tmp;
set tmp;
drop age;
run;
在这种情况下,这是一个非常无害的示例,您很幸运,SAS 只是发出警告。根据数据步骤的不同,它可能很容易产生错误,例如:
data tmp;
set tmp (rename=(age=blah));
run;
或者更糟的是,它可能不会生成任何错误或警告,并且会像下面的代码那样更改预期结果:
data tmp;
set tmp;
weight = log(weight);
run;
我们的目的是对权重变量应用简单的对数转换以准备建模,但如果我们不小心 运行 第二次执行该步骤,我们将计算 log(log(weight))。不会给出任何警告或错误,并且查看数据集不会立即明显看出任何错误。
IMO,你最好创建迭代数据集,即。 tmp1、tmp2、tmp3 等等...对于以某种方式更新数据集的每个进程。 Space 比花时间调试便宜多了。