楼主: stata18
5588 11

[实际应用] 在sas中修改变量属性遇到的一个问题 [推广有奖]

  • 3关注
  • 6粉丝

教授

70%

还不是VIP/贵宾

-

TA的文库  其他...

MyLib

威望
1
论坛币
4225 个
通用积分
102.4402
学术水平
15 点
热心指数
31 点
信用等级
16 点
经验
157348 点
帖子
728
精华
0
在线时间
1917 小时
注册时间
2010-8-13
最后登录
2024-4-20

+2 论坛币
k人 参与回答

经管之家送您一份

应届毕业生专属福利!

求职就业群
赵安豆老师微信:zhaoandou666

经管之家联合CDA

送您一个全额奖学金名额~ !

感谢您参与论坛问题回答

经管之家送您两个论坛币!

+2 论坛币
在合并多个数据集时,会遇到同一个变量在不同数据集里数据类型不同的情况,需要修改为一致再合并。为此,写了一个宏程序,但是在执行时发现一个奇怪的问题。程序如下:
%macro attrib;
data _null_;set dsn nobs=obsnum;      * 数据集dsn包含需要修改变量属性的数据集的名字,                                                       * 这些数据集有共同的变量:obs,但是属性有的是字符型,有的是数值型;
call symput('total',left(obsnum));
run;
%put &total.;

%do i=&total. %to 1 %by -1;
     data _null_;set dsn;
     if _n_=&i. then call symput('dsn',strip(dsn));
     run;

     proc contents data=&dsn. out=var(keep=name type where=(lowcase(name)="obs")) noprint;run;
     data _null_;set Var;
     if lowcase(name)="obs" & type=2 then call symput('obs',left(type));
     run;
     %if %symexist(obs) %then %do;
                                     data &dsn.(rename=(trans_obs=obs));set &dsn.;
                                     trans_obs=obs/1;drop obs;run;
                                 %end;
     %symdel obs/nowarn;
%end;

proc delete data=dsn var;run;
%mend attrib;

%attrib;


程序中红色部分如果修改为:%do i=1 %to &total.;则执行结果不同。反复测试也没有发现问题所在,不知道有无高手遇到过类似问题,或者能指出这个程序问题所在?
不同数据集中该变量:obs属性不同,设定为均修改为数值型变量。


二维码

扫码加我 拉你入群

请注明:姓名-公司-职位

以便审核进群资格,未注明则拒绝

关键词:contents Content symput rename delete

a数据集长什么样子?

使用道具

藤椅
stata18 发表于 2016-3-2 16:53:03 |只看作者 |坛友微信交流群
孤单的我们 发表于 2016-3-2 16:47
a数据集长什么样子?
data _null_;set dsn nobs=obsnum;

数据集dsn包含需要修改变量属性的数据集的名字,这些数据集有共同的变量:obs,但是属性有的是字符型,有的是数值型

使用道具

试了一下,可以运行啊

  1. data a;
  2.         obs=1;z=1;
  3. run;

  4. data b;
  5.         obs="3";x=1;
  6. run;

  7. data dsn;
  8.         dsn="a";output;
  9.         dsn="b";output;
  10. run;

  11. %macro attrib;
  12. data _null_;set dsn nobs=obsnum;      * 数据集dsn包含需要修改变量属性的数据集的名字,                                                       * 这些数据集有共同的变量:obs,但是属性有的是字符型,有的是数值型;
  13. call symput('total',left(obsnum));
  14. run;
  15. %put &total.;

  16. %do i=&total. %to 1 %by -1;
  17.      data _null_;set dsn;
  18.      if _n_=&i. then call symput('dsn',strip(dsn));
  19.      run;

  20.      proc contents data=&dsn. out=var(keep=name type where=(lowcase(name)="obs")) noprint;run;
  21.      data _null_;set Var;
  22.      if lowcase(name)="obs" & type=2 then call symput('obs',left(type));
  23.      run;
  24.      %if %symexist(obs) %then %do;
  25.                                      data &dsn.(rename=(trans_obs=obs));set &dsn.;
  26.                                      trans_obs=obs/1;drop obs;run;
  27.                                  %end;
  28.      %symdel obs/nowarn;
  29. %end;

  30. proc delete data=dsn var;run;
  31. %mend attrib;

  32. %attrib;
复制代码

使用道具

报纸
stata18 发表于 2016-3-2 17:30:12 |只看作者 |坛友微信交流群
孤单的我们 发表于 2016-3-2 17:23
试了一下,可以运行啊
可以运行。只是运行时log中提示不同。红色语句不同,提示不一样。
一种提示obs未初始化,另外一种不提示。
我的是多个数据集,例如:a中该变量是字符型,b中是数值型,c中无该变量(对于c数据集的提示可能是:obs未初始化,或者是无任何异常提示,顺利运行)。感觉执行顺序不同,%if部分的编译结果不同,导致两种顺序的程序执行起来结果不同(提示不同)。我没有理解为何会这样?程序中特意删除了生成的宏变量:%symdel obs/nowarn;

使用道具

if lowcase(name)="obs" & type=2 then call symput('obs',left(type));
call symputx产生的宏变量,在循环语句结束时应当删去。
未初始化的原因是:c中无该变量时,宏变量obs保留上一次b的结果,%if %symexist(obs) %then %do;判断为真。

使用道具

7
stata18 发表于 2016-3-3 11:58:56 |只看作者 |坛友微信交流群
孤单的我们 发表于 2016-3-3 09:18
if lowcase(name)="obs" & type=2 then call symput('obs',left(type));
call symputx产生的宏变量,在循环 ...
未初始化的原因是:c中无该变量时,宏变量obs保留上一次b的结果,%if %symexist(obs) %then %do;判断为真。

从执行结果和提示看,好像是保留了上一次的宏变量值,但是我在程序中加了:%symdel obs/nowarn;这个语句啊。还尝试过在不同位置添加(                       %do i=&total. %to 1 %by -1;之后;
                      前一句对应的%end;之前;
                      以及修改变量属性的那个循环中),
但是结果不变。

使用道具

8
孤单的我们 发表于 2016-3-3 13:13:52 |只看作者 |坛友微信交流群
%SYMDEL:Deletes the specified variables(s) from the macro global symbol table.

使用道具

9
stata18 发表于 2016-3-3 16:24:45 |只看作者 |坛友微信交流群
孤单的我们 发表于 2016-3-3 13:13
%SYMDEL:Deletes the specified variables(s) from the macro global symbol table.
看来就是这里出问题了,只是不知道该如何修改?

使用道具

  1. data a;
  2.         obs=1;z=1;
  3. run;

  4. data b;
  5.         obs="3";x=1;
  6. run;

  7. data c;
  8.         t=12;
  9. run;

  10. data dsn;
  11.         dsn="a";output;
  12.         dsn="b";output;
  13.         dsn="c";output;
  14. run;

  15. %macro attrib;
  16. data _null_;set dsn nobs=obsnum;
  17. call symput('total',left(obsnum));
  18. run;
  19. %put &total.;

  20. /*%do i=&total. %to 1 %by -1;*/
  21. %do i=1 %to &total;
  22.         %let obs=;
  23.      data _null_;set dsn;
  24.      if _n_=&i. then call symput('dsn',strip(dsn));
  25.      run;

  26.      proc contents data=&dsn. out=var(keep=name type where=(lowcase(name)="obs")) noprint;run;
  27.      data _null_;set Var;
  28.      if lowcase(name)="obs" & type=2 then call symput('obs',left(type));
  29.      run;
  30.          %if &obs> %then %do;%put "obs"=&obs;
  31.              data &dsn.(rename=(trans_obs=obs));set &dsn.;
  32.                 trans_obs=obs/1;drop obs;
  33.                 run;
  34.          %end;
  35. %end;

  36. proc delete data=dsn var;run;
  37. %mend attrib;

  38. %attrib;
复制代码
已有 1 人评分论坛币 学术水平 热心指数 信用等级 收起 理由
stata18 + 5 + 5 + 5 + 5 精彩帖子

总评分: 论坛币 + 5  学术水平 + 5  热心指数 + 5  信用等级 + 5   查看全部评分

使用道具

您需要登录后才可以回帖 登录 | 我要注册

本版微信群
加好友,备注cda
拉您进交流群

京ICP备16021002-2号 京B2-20170662号 京公网安备 11010802022788号 论坛法律顾问:王进律师 知识产权保护声明   免责及隐私声明

GMT+8, 2024-5-10 14:33