楼主: B.N.F
7551 62

peeklong [推广有奖]

31
B.N.F 发表于 2013-9-10 23:12:36
zhou.wen 发表于 2013-9-10 23:10
APP function 据说只有5%的sasor才精通
APP function 是什么啊?

32
zhou.wen 发表于 2013-9-10 23:24:57
addr peek poke
Practice Is The Best Teacher!

33
zhou.wen 发表于 2013-9-11 00:00:52
B.N.F 发表于 2013-9-10 23:10
这个代码为什么通不过呢?

data b;
%macro main;
data b;
array a(1000) $ ;
do i=1 to 1000;
a(i)=put(i,pib8.);
end;
e=addrlong(a(1));
call symputx("e",e);
_error_=dosubl( "
data a;
do i=1 to 12;
ans=peeklong(put(input('&e',pib8.)+8*(i-1),pib8.),8);
output;
end;
run;
quit;
");
run;
%mend;

%main;
嵌到一个宏里?
Practice Is The Best Teacher!

34
zhou.wen 发表于 2013-9-11 00:34:37
dosubl is really a useful function!!!
DOSUBL is an experimental function in SAS 9.3 that takes a character value and executes the value as SAS code. DOSUBL does not return until the SAS code completes execution. DOSUB is similar to DOSUBL, yet it takes a fileref for a file that contains SAS code. DOSUB reads the file into memory and executes the contents as SAS code.
Both DOSUBL and DOSUB return zero if the code was able to execute and nonzero if the code did not execute. For example, if DOSUB could not read the input file or allocate enough memory to hold the file contents, it returns a nonzero value.
Here is an example of using DOSUBL from a DATA step to create a data set with PROC SQL:
4
data _null_;
rc = dosubl('proc sql;
create table work.regions as
select distinct region from sashelp.shoes;');
run;
When DOSUBL is called, it does not return until the SAS code completes. The SAS code passed to DOSUBL uses PROC SQL to create a data set named WORK.REGIONS that contains all the unique values for REGION in SASHELP.SHOES. If you wanted to operate on the distinct values within the same step, you can use the DATA step OPEN and FETCH functions to open and read WORK.REGIONS. The SET statement cannot be used because SET opens the data set before the step begins execution and the data set would not have been created yet.
Practice Is The Best Teacher!

35
B.N.F 发表于 2013-9-11 05:05:15
zhou.wen 发表于 2013-9-11 00:00
%macro main;
data b;
array a(1000) $ ;
不知道为什么第一次执行会报错,
重复执行才没有报错。。。

36
zhou.wen 发表于 2013-9-11 10:24:20
B.N.F 发表于 2013-9-11 05:05
不知道为什么第一次执行会报错,
重复执行才没有报错。。。
我一开始执行的时候没有出错,不过结果不对
你能说下你实现数据共享的思路是什么么?
感觉你对sas的宏用的不是很熟,但是对dosubl这种新函数又比较了解,还有app fuction这种基本没人用的东西反而比较了解,所以比较好奇你的背景,难道是有高人指点么
Practice Is The Best Teacher!

37
zhou.wen 发表于 2013-9-11 11:39:28
sxlion 发表于 2013-9-10 22:20
"我想把array进行数据共享,这样多个宏和多个data步,就不用重复的set了。"

这个问题 n年前讨论过,目 ...
9.3之后出了dosubl,可以实现这个目标
http://support.sas.com/resources ... ings12/227-2012.pdf
http://support.sas.com/resources ... ings13/032-2013.pdf
Practice Is The Best Teacher!

38
zhou.wen 发表于 2013-9-11 13:36:02
之前写的宏的处理机制我自己都不太理解
下面的做法更适合
data b;
array a(1000) $ ;
do i=1 to 1000;
a(i)=put(i,pib8.);
end;
e=addrlong(a(1));
call symputx("e",e);
_error_=dosubl( "
data a;
do i=1 to 12;
ans=peeklong(put(input(symget('e'),pib8.)+8*2*(i-1),pib8.),8);
output;
end;
run;
quit;
");
run;
Practice Is The Best Teacher!

39
zhou.wen 发表于 2013-9-11 14:03:29
补充一下,上面的代码也应该是比较好理解的,但是外部嵌套宏之后,宏的编译不是应该在data之前
因此,你第一次运行%main;的时候宏变量e没有赋值,所以出错,但是第二次运行%main;后宏变量e已经赋了值,所以第二次运行结果正确
这里还有个小问题,宏变量e赋的是data b中变量a(1)的内存地址,我一开始理解data步结束后内存地址会释放,也就是说下次运行data b步的时候a(1)的地址应该有变化才对
但是从结果来看,第二次运行%main;宏变量e正确的取到了a(1)的内存地址,也就是说第二次运行data b的时候,虽然数据集是重新生成的,但是给变量a(1)分配的内存地址跟第一次运行相比并没有改变。于是我猜测可能是sas内部有缓存机制
下面做一些实验:
option nonotes nosource;
%put Firt Time Run:data a address is;
data a;
b=1;c=2;
add=addrlong(b);
put add hex16.;
run;
%put Firt Time Run:data a1 address is;
data a1;
x=1;y=1;z=2;
add=addrlong(x);
put add hex16.;
run;
%put Second Time Run:data a address is;
data a;
b=1;c=2;
add=addrlong(b);
put add hex16.;
run;
结果为:
Firt Time Run:data a address is
0881AA0C00000000
Firt Time Run:data a1 address is
3881AA0C00000000
Second Time Run:data a address is
0881AA0C00000000
可以猜测提交过的代码在,在sas中有缓存,所以相同的变量的内存地址没有发生变化,这样也就解释了为什么第二次运行%main;可以成功。
上面的大部分内容为个人理解,希望各路大神拍砖。
Practice Is The Best Teacher!

40
B.N.F 发表于 2013-9-11 22:21:54
zhou.wen 发表于 2013-9-11 13:36
之前写的宏的处理机制我自己都不太理解
下面的做法更适合
data b;
1    data b;
2    array a(1000) $ ;
3    do i=1 to 1000;
4    a(i)=put(i,pib8.);
5    end;
6    e=addrlong(a(1));
7    call symputx("e",e);
8    _error_=dosubl( "
9    data a;
10   do i=1 to 12;
11   ans=peeklong(put(input(symget('e'),pib8.)+8*2*(i-1),pib8.),8);
12   output;
13   end;
14   run;
15   quit;
16   ");
17   run;

ERROR: 出现了异常。
请与技术支持人员联系,并向他们提供下列回溯信息:

SAS 任务名称为 [DATASTEP]
ERROR:  Read Access Violation DATASTEP
Exception occurred at (0D811518)
Task Traceback
Address   Frame     (DBGHELP API Version 4.0 rev 5)
000000000D811518  000000002A22FA60  uwusysap:tkvercn1+0x4D8
000000000C8A694E  000000002A22FA98  sase7:tkvercn1+0x1590E

NOTE: 参数“1”(用于函数“PEEKLONG”)无效,位置: 行 0 列 25。
ERROR: 出现了异常。
请与技术支持人员联系,并向他们提供下列回溯信息:

SAS 任务名称为 [DATASTEP]
ERROR:  Read Access Violation DATASTEP
Exception occurred at (0D811518)
Task Traceback
Address   Frame     (DBGHELP API Version 4.0 rev 5)
000000000D811518  000000002A22FA60  uwusysap:tkvercn1+0x4D8

NOTE: 参数“1”(用于函数“PEEKLONG”)无效,位置: 行 0 列 25。
ERROR: 出现了异常。
请与技术支持人员联系,并向他们提供下列回溯信息:

SAS 任务名称为 [DATASTEP]
ERROR:  Read Access Violation DATASTEP
Exception occurred at (0D811518)
Task Traceback
Address   Frame     (DBGHELP API Version 4.0 rev 5)
000000000D811518  000000002A22FA60  uwusysap:tkvercn1+0x4D8

NOTE: 参数“1”(用于函数“PEEKLONG”)无效,位置: 行 0 列 25。
ERROR: 出现了异常。
请与技术支持人员联系,并向他们提供下列回溯信息:

SAS 任务名称为 [DATASTEP]
ERROR:  Read Access Violation DATASTEP
Exception occurred at (0D811518)
Task Traceback
Address   Frame     (DBGHELP API Version 4.0 rev 5)
000000000D811518  000000002A22FA60  uwusysap:tkvercn1+0x4D8

NOTE: 参数“1”(用于函数“PEEKLONG”)无效,位置: 行 0 列 25。
ERROR: 出现了异常。
请与技术支持人员联系,并向他们提供下列回溯信息:

SAS 任务名称为 [DATASTEP]
ERROR:  Read Access Violation DATASTEP
Exception occurred at (0D811518)
Task Traceback
Address   Frame     (DBGHELP API Version 4.0 rev 5)
000000000D811518  000000002A22FA60  uwusysap:tkvercn1+0x4D8

NOTE: 参数“1”(用于函数“PEEKLONG”)无效,位置: 行 0 列 25。
ERROR: 出现了异常。
请与技术支持人员联系,并向他们提供下列回溯信息:

SAS 任务名称为 [DATASTEP]
ERROR:  Read Access Violation DATASTEP
Exception occurred at (0D811518)
Task Traceback
Address   Frame     (DBGHELP API Version 4.0 rev 5)
000000000D811518  000000002A22FA60  uwusysap:tkvercn1+0x4D8

NOTE: 参数“1”(用于函数“PEEKLONG”)无效,位置: 行 0 列 25。
ERROR: 出现了异常。
请与技术支持人员联系,并向他们提供下列回溯信息:

SAS 任务名称为 [DATASTEP]
ERROR:  Read Access Violation DATASTEP
Exception occurred at (0D811518)
Task Traceback
Address   Frame     (DBGHELP API Version 4.0 rev 5)
000000000D811518  000000002A22FA60  uwusysap:tkvercn1+0x4D8

NOTE: 参数“1”(用于函数“PEEKLONG”)无效,位置: 行 0 列 25。
ERROR: 出现了异常。
请与技术支持人员联系,并向他们提供下列回溯信息:

SAS 任务名称为 [DATASTEP]
ERROR:  Read Access Violation DATASTEP
Exception occurred at (0D811518)
Task Traceback
Address   Frame     (DBGHELP API Version 4.0 rev 5)
000000000D811518  000000002A22FA60  uwusysap:tkvercn1+0x4D8

NOTE: 参数“1”(用于函数“PEEKLONG”)无效,位置: 行 0 列 25。
ERROR: 出现了异常。
请与技术支持人员联系,并向他们提供下列回溯信息:

SAS 任务名称为 [DATASTEP]
ERROR:  Read Access Violation DATASTEP
Exception occurred at (0D811518)
Task Traceback
Address   Frame     (DBGHELP API Version 4.0 rev 5)
000000000D811518  000000002A22FA60  uwusysap:tkvercn1+0x4D8

NOTE: 参数“1”(用于函数“PEEKLONG”)无效,位置: 行 0 列 25。
ERROR: 出现了异常。
请与技术支持人员联系,并向他们提供下列回溯信息:

SAS 任务名称为 [DATASTEP]
ERROR:  Read Access Violation DATASTEP
Exception occurred at (0D811518)
Task Traceback
Address   Frame     (DBGHELP API Version 4.0 rev 5)
000000000D811518  000000002A22FA60  uwusysap:tkvercn1+0x4D8

NOTE: 参数“1”(用于函数“PEEKLONG”)无效,位置: 行 0 列 25。
ERROR: 出现了异常。
请与技术支持人员联系,并向他们提供下列回溯信息:

SAS 任务名称为 [DATASTEP]
ERROR:  Read Access Violation DATASTEP
Exception occurred at (0D811518)
Task Traceback
Address   Frame     (DBGHELP API Version 4.0 rev 5)
000000000D811518  000000002A22FA60  uwusysap:tkvercn1+0x4D8

NOTE: 参数“1”(用于函数“PEEKLONG”)无效,位置: 行 0 列 25。
ERROR: 出现了异常。
请与技术支持人员联系,并向他们提供下列回溯信息:

SAS 任务名称为 [DATASTEP]
ERROR:  Read Access Violation DATASTEP
Exception occurred at (0D811518)
Task Traceback
Address   Frame     (DBGHELP API Version 4.0 rev 5)
000000000D811518  000000002A22FA60  uwusysap:tkvercn1+0x4D8

NOTE: 参数“1”(用于函数“PEEKLONG”)无效,位置: 行 0 列 25。
i=13 ans=. _ERROR_=1 _N_=1
NOTE: 在以下位置无法执行算术运算。运算结果已设为缺失值。
      每个位置的指定方式: (次数)(行:列)。
      12,位置: 0:25。
NOTE: 数据集 WORK.A 有 12 个观测和 2 个变量。
NOTE: “DATA 语句”所用时间(总处理时间):
      实际时间          0.12 秒
      CPU 时间          0.09 秒


NOTE: 数据集 WORK.B 有 1 个观测和 1002 个变量。
NOTE: “DATA 语句”所用时间(总处理时间):
      实际时间          0.21 秒
      CPU 时间          0.15 秒


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

本版微信群
加好友,备注cda
拉您进交流群
GMT+8, 2026-2-18 04:51