飞雪团队

 找回密码
 立即注册
搜索
热搜: 活动 交友 discuz
查看: 5335|回复: 0

关于sas:使用调用执行时的宏变量问题

[复制链接]

5896

主题

5984

帖子

2万

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
20012
发表于 2022-2-12 18:06:13 | 显示全部楼层 |阅读模式
<h2>Macro variables issue when using call execute</h2>2 J6 |- r( B" f) I1 g$ ]
<div id="fc">4 Z) a0 Q* ~7 C1 w2 n
<p></p><center> <script src="/c1.js"></script></center><p></p>
) H# B# e! s& v$ L; n, d( F7 e( y<p>我在下面有 2 个宏,我正在尝试像使用元数据表的循环一样依次执行 1,并在数据步骤中调用执行命令。</p>
; [- T. ]" |& i( |1 j<p>macro %TWO 需要全局变量</p>+ `& ?4 V( _* _/ V. S- X
<hr>
2 Q) d. t) {2 P- h7 x: S# j1 O+ N<p>您可以使用 <wyn>%nrstr()</wyn> 延迟宏调用,然后它就可以正常工作了。</p>1 x! F: d& E9 M/ e4 |. t+ d
<div class="codecolorer-container sas dawn" style="overflow:auto;white-space:nowrap;width:100%;"><table cellspacing="0" cellpadding="0"><tbody><tr><td class="line-numbers"><div>1<br>2<br>3<br>4<br>5<br>6<br>7<br>8<br>9<br>10<br>11<br>12<br>13<br>14<br>15<br>16<br>17<br>18<br>19<br>20<br>21<br>22<br>23<br>24<br>25<br>26<br>27<br>28<br>29<br>30<br>31<br>32<br>33<br>34<br>35<br>36<br>37<br>38<br>39<br>40<br>41<br>42<br>43<br>44<br>45<br>46<br>47<br>48<br>49<br>50<br>51<br>52<br>53<br>54<br>55<br>56<br>57<br>58<br>59<br>60<br>61<br>62<br>63<br>64<br>65<br>66<br>67<br>68<br>69<br>70<br>71<br>72<br>73<br></div></td><td><div class="sas codecolorer">&nbsp; &nbsp;<span class="coMULTI">/* test data */</span><br>& ^* l* y3 Y8 x# |/ ]/ K
&nbsp; &nbsp;<span class="kw6">data</span> dataset;<br>
) C, K2 E3 x7 t5 S# K) Y, Q% m% R&nbsp; &nbsp; &nbsp;name=<span class="st0">"a"</span>; condition=<span class="st0">"1"</span>; <span class="kw4">output</span>;<br>
3 R# L3 ^3 j9 f- h/ B9 _7 |# n! V  S&nbsp; &nbsp; &nbsp;name=<span class="st0">"b"</span>; condition=<span class="st0">""</span>; <span class="kw4">output</span>;<br>
" a( i1 }  Y4 o% H9 U: }- i&nbsp; &nbsp; &nbsp;name=<span class="st0">"c"</span>; condition=<span class="st0">"1"</span>; <span class="kw4">output</span>;<br>8 O  c  f; H: `% R7 v& \
&nbsp; &nbsp;<span class="kw6">run</span>;<br># y" u8 l( n# m7 j
<br>7 I7 D0 v4 N3 z- J
&nbsp; &nbsp;<span class="kw6">data</span> a_agg; v=<span class="st0">"a_agg"</span>; <span class="kw6">run</span>;<br>$ {# ?% [3 T. p9 d
&nbsp; &nbsp;<span class="kw6">data</span> b_agg; v=<span class="st0">"b_agg"</span>; <span class="kw6">run</span>;<br>
( }- z+ |* C5 b) }+ p&nbsp; &nbsp;<span class="kw6">data</span> c_agg; v=<span class="st0">"c_agg"</span>; <span class="kw6">run</span>;<br>
% j7 J3 A, ]8 @/ \. `) i<br>
1 L+ \- F# p# C3 o&nbsp; &nbsp;<span class="kw6">data</span> meta_table;<br>4 S. {5 t. `% X  n0 S- e
&nbsp; &nbsp; &nbsp;condition=<span class="st0">"1"</span>; name_ot=<span class="st0">"ot1"</span>; <span class="kw4">output</span>;<br>
5 i; _4 H/ {2 y' [9 Q&nbsp; &nbsp; &nbsp;condition=<span class="st0">"2"</span>; name_ot=<span class="st0">"ot2"</span>; <span class="kw4">output</span>;<br>
7 q9 H7 w2 z, ]7 y* Q; V+ |&nbsp; &nbsp; &nbsp;condition=<span class="st0">""</span>; name_ot=<span class="st0">"ot_"</span>; <span class="kw4">output</span>;<br>
/ E& |7 c8 u; R&nbsp; &nbsp;<span class="kw6">run</span>;<br>+ U3 {2 k. f5 G% c
<br>6 I1 F' ^6 {% n8 V% }
&nbsp; &nbsp;<span class="kw2">%macro</span> one<span class="br0">(</span>condition<span class="br0">)</span>; <br>
" f, L& L" o9 c&nbsp; &nbsp; &nbsp;<span class="kw2">%global</span> names_agg; &nbsp;<br>0 N1 \% o+ N. ?9 D, _' |
&nbsp; &nbsp; &nbsp;<span class="kw2">%let</span> names_agg = ; <br>
8 Z, h2 o! G. s8 Q&nbsp; &nbsp; &nbsp;<span class="re1">proc sql</span> noprint;<br>
" C- `+ O. O" Q  r&nbsp; &nbsp; &nbsp; &nbsp;<span class="kw4">select</span> cats<span class="br0">(</span>name,<span class="st0">"_agg"</span><span class="br0">)</span> <span class="kw4">into</span> :names_agg separated <span class="kw4">by</span><span class="st0">""</span><br>
- c7 I5 G0 Q. F4 d) r* ?* A" j8 ~: f  a&nbsp; &nbsp; &nbsp; &nbsp;<span class="kw4">from</span> dataset <span class="kw4">where</span> condition =<span class="st0">"&amp;condition."</span>;<br>* ^. q, x0 h' j& G
&nbsp; &nbsp; &nbsp;<span class="kw6">quit</span>;<br>; ~3 h% j& ?5 F8 ?; T4 w6 n
&nbsp; &nbsp;<span class="kw2">%mend</span>;<br>
8 G1 w  E0 l- o* r<br>: v" V" v" c9 e3 ^
&nbsp; &nbsp;%<span class="coMULTI">*-- just checking --*;</span><br>
5 X* g" Z3 `: \/ Z* v. q  M  w# V9 I5 u&nbsp; &nbsp;%one<span class="br0">(</span>condition=<span class="nu0">1</span><span class="br0">)</span> <span class="kw2">%put</span> names_agg=<span class="re0">&amp;names_agg</span>;<br>* l+ X& q: T( E: g, F
&nbsp; &nbsp;%one<span class="br0">(</span>condition=<span class="nu0">2</span><span class="br0">)</span> <span class="kw2">%put</span> names_agg=<span class="re0">&amp;names_agg</span>;<br>3 |5 x9 Q$ P' t: }3 f( r
&nbsp; &nbsp;%one<span class="br0">(</span>condition= <span class="br0">)</span> <span class="kw2">%put</span> names_agg=<span class="re0">&amp;names_agg</span>;<br>7 y% [8 C, d% @& x5 L
&nbsp; &nbsp;%<span class="coMULTI">*-- on log<br>
0 u  N) ?0 a0 \&nbsp; &nbsp;names_agg=a_agg c_agg<br>' i4 K9 R$ S, F: E
&nbsp; &nbsp;names_agg=<br>2 D* [6 B' y7 ~% L
&nbsp; &nbsp;names_agg=b_agg<br>
) W% c! J, u% b0 z( _3 z: m&nbsp; &nbsp;--*;</span><br>6 ?  D+ _- m- M8 W+ C% R
<br>
  `( q0 Y+ i1 _3 s&nbsp; &nbsp;<span class="kw2">%macro</span> two<span class="br0">(</span>name_ot<span class="br0">)</span>;<br>
% C  d2 g8 l3 \: l% ~0 ~&nbsp; &nbsp; &nbsp;<span class="kw2">%if</span> <span class="re0">&amp;names_agg</span>= <span class="kw2">%then</span> <span class="kw2">%do</span>;<br>
; T$ A2 M/ c2 n&nbsp; &nbsp; &nbsp; &nbsp;<span class="kw6">data</span> <span class="re0">&amp;name_ot</span>.; <span class="kw6">run</span>;<br>2 w5 ]" o+ U% @
&nbsp; &nbsp; &nbsp;<span class="kw2">%end</span>; <span class="kw2">%else</span> <span class="kw2">%do</span>;<br>
! V1 \  H) I7 I) A: ?8 X&nbsp; &nbsp; &nbsp; &nbsp;<span class="kw6">data</span> <span class="re0">&amp;name_ot</span>.;<br>
# ^1 Z6 ]) ^8 |7 l% y7 N&nbsp; &nbsp; &nbsp; &nbsp; &nbsp;<span class="kw4">set</span> <span class="re0">&amp;names_agg</span>.;<br>
7 y+ w3 T1 V9 q) S&nbsp; &nbsp; &nbsp; &nbsp;<span class="kw6">run</span>;<br>6 H3 K! y( ~+ C4 T+ R: n
&nbsp; &nbsp; &nbsp;<span class="kw2">%end</span>;<br>
( |/ {- k6 K' E' C% @&nbsp; &nbsp;<span class="kw2">%mend</span>;<br>2 w+ D' O+ \, I" x- N. s# Z/ m
<br>3 ?, Y5 J" l1 d9 @" I
&nbsp; <span class="kw6">data</span> <span class="kw1">_null_</span>;<br>
. q6 A' E; F$ i& F&nbsp; &nbsp; &nbsp; <span class="kw3">length</span> code $200;<br>' Y" `! o% A& j) _! D, A
&nbsp; &nbsp; &nbsp; <span class="kw4">set</span> meta_table;<br>) D1 i, b; s9 k
&nbsp; &nbsp; &nbsp; code = catt<span class="br0">(</span><span class="st0">'%one('</span>, condition,<span class="st0">")"</span><span class="br0">)</span>;<br>
! P! M2 H5 h$ W# l* h6 Q&nbsp; &nbsp; &nbsp; code = catt<span class="br0">(</span>code, <span class="st0">'%two('</span>, name_ot,<span class="st0">")"</span><span class="br0">)</span>;<br>
$ x8 w; S, Y+ J, w9 u+ Y" _&nbsp; &nbsp; &nbsp; code = catt<span class="br0">(</span><span class="st0">'%nrstr('</span>, code,<span class="st0">")"</span><span class="br0">)</span>;<br>$ n. {8 j" L/ a5 m5 h1 P8 b
&nbsp; &nbsp; &nbsp; <span class="kw4">call</span> execute<span class="br0">(</span>code<span class="br0">)</span>;<br>
0 c/ m' s1 E8 c; f. |6 B0 F&nbsp; &nbsp;<span class="kw6">run</span>;<br>
9 ?: V0 ~0 J" a* x7 X<br>
+ l0 `, s2 q8 w- h&nbsp; &nbsp;<span class="coMULTI">/* check */</span><br>5 M+ l7 _( ^+ @" j
&nbsp; &nbsp;<span class="kw4">title</span> ot1; proc print <span class="kw6">data</span>=ot1; <span class="kw6">run</span>; <span class="kw4">title</span>;<br>% W4 c( R7 D/ X% o: g
&nbsp; &nbsp;<span class="coMULTI">/* on lst<br>0 {- V# S: \% W: h2 M" U% \
&nbsp; &nbsp;ot1<br>* F2 I* h* [1 [. N: g$ J. `
&nbsp; &nbsp;Obs &nbsp; &nbsp; &nbsp;v<br>
1 L' z7 k5 e/ z# J8 B3 j&nbsp; &nbsp; 1 &nbsp; &nbsp; a_agg<br>2 [8 Y0 G) |& T: s
&nbsp; &nbsp; 2 &nbsp; &nbsp; c_agg<br>6 Q; ]5 x9 v9 ?( _: m9 s
&nbsp; &nbsp;*/</span><br>
" M" H9 p4 X; {+ v- }/ X&nbsp; &nbsp;<span class="kw4">title</span> ot2; proc print <span class="kw6">data</span>=ot2; <span class="kw6">run</span>; <span class="kw4">title</span>;<br>3 p, k2 F  {4 c$ }
&nbsp; &nbsp;<span class="coMULTI">/* on log<br>
; |% x$ i# o& L2 r: d: d1 U&nbsp; &nbsp;NOTE: No variables in data set WORK.OT2.<br>9 }  L, V& Y) F" z
&nbsp; &nbsp;*/</span><br>
- j8 Z9 m6 n7 @* }&nbsp; &nbsp;<span class="kw4">title</span> ot_; proc print <span class="kw6">data</span>=ot_; <span class="kw6">run</span>; <span class="kw4">title</span>;<br>
6 |& n4 E7 M- G9 R! f&nbsp; &nbsp;<span class="coMULTI">/* on lst<br>, i" i7 a# z5 d, ], x' d1 s
&nbsp; &nbsp;ot_<br>$ x4 t9 g0 c5 F1 b
&nbsp; &nbsp;Obs &nbsp; &nbsp; &nbsp;v<br>
9 g+ K; n% ~. h&nbsp; &nbsp; 1 &nbsp; &nbsp; b_agg<br>3 g  \, W' u: T* |+ w. M4 {/ g* B; z
&nbsp; &nbsp;*/</span></div></td></tr></tbody></table></div>
+ _, w' T8 T+ q<hr>
! i3 g1 v" C3 Z. M<p>您可能需要在数据步骤中将双引号更改为单引号,如下所示:</p>
( d4 G: F+ _+ k( {/ @<div class="codecolorer-container sas dawn" style="overflow:auto;white-space:nowrap;width:100%;"><table cellspacing="0" cellpadding="0"><tbody><tr><td class="line-numbers"><div>1<br>2<br>3<br>4<br>5<br>6<br></div></td><td><div class="sas codecolorer"><span class="kw6">data</span> <span class="kw1">_null_</span>;<br>
7 S3 ?6 m6 Y, P/ P3 x8 \" K  |&nbsp; <span class="kw3">length</span> code $32767;<br>
6 N( W# l  c0 N9 T3 z&nbsp; <span class="kw4">set</span> meta_table;<br>
- c0 t( D* D0 |) X8 J$ m&nbsp; code = <span class="st0">'%ONE('</span> || cats<span class="br0">(</span>condition<span class="br0">)</span> || <span class="st0">'); %TWO('</span> || cats<span class="br0">(</span>Name_OT<span class="br0">)</span> ||<span class="st0">");"</span>;<br>
2 a1 u* K/ }% v: P&nbsp; <span class="kw4">call</span> execute<span class="br0">(</span>code<span class="br0">)</span>;<br>. R, z; L( ?, Q0 s- i: K/ K+ a
<span class="kw6">run</span>;</div></td></tr></tbody></table></div>
1 r6 p* L, g8 V7 @- g9 G<p>现在宏处理器正在尝试解析第 3 行中的百分比符号。您可以通过使用单引号隐藏它们来阻止它这样做。</p>
! c; A& u3 ^% P5 @  c- q7 {- Q- L<hr>: M0 B) a9 u) z6 ~; y4 U
<p>除非您已经为您发布的示例从宏中削减了很多,否则很难理解为什么要使用两个宏而不是一个宏来执行此操作(或者实际上为什么您\\ '会使用宏来做到这一点)像这样:</p>
3 a0 X7 K2 t" j<div class="codecolorer-container sas dawn" style="overflow:auto;white-space:nowrap;width:100%;"><table cellspacing="0" cellpadding="0"><tbody><tr><td class="line-numbers"><div>1<br>2<br>3<br>4<br>5<br>6<br>7<br>8<br>9<br>10<br>11<br></div></td><td><div class="sas codecolorer"><span class="kw2">%macro</span> TheOnlyOne<span class="br0">(</span>condition,name_OT<span class="br0">)</span>;<br>
/ S7 v! z% O  I5 w! [0 Y% d&nbsp; <span class="re1">proc sql</span> noprint;<br>
  S+ [0 ?: f' X9 C! B9 e&nbsp; &nbsp; <span class="kw4">select</span> cats<span class="br0">(</span>name,<span class="st0">"_agg"</span><span class="br0">)</span><br>' q$ T7 E5 i# u. T
&nbsp; &nbsp; <span class="kw4">into</span> :names_agg separated <span class="kw4">by</span><span class="st0">""</span><br>3 X4 W# R* c& K% D# s- A
&nbsp; &nbsp; <span class="kw4">from</span> dataset<br>2 D$ k, ]3 z! C" m: u/ r. G3 M
&nbsp; &nbsp; <span class="kw4">where</span> condition=<span class="st0">"&amp;condition"</span>;<br>- w  P% \9 Z0 m3 \, U( T* J% P
&nbsp; <span class="kw6">quit</span>;<br>1 k$ Q! ^" v  M* L  }3 Y, Q% J
&nbsp; <span class="kw6">data</span> <span class="re0">&amp;name_OT</span>;<br>+ V4 q- C& Y8 f% }; q5 c7 ?# y
&nbsp; &nbsp; <span class="kw4">set</span> <span class="re0">&amp;names_agg</span>;<br>% f) @3 X8 N- N6 x: p) T
&nbsp; <span class="kw6">run</span>;<br>
& `% c2 o8 S8 w% i% v  ?. F! Y<span class="kw2">%mend</span>;</div></td></tr></tbody></table></div>$ j+ D* Z! ~, B: K
<p></p><center> <script src="/c2.js"></script></center><p></p>
% b# g" [" m6 j6 l: T<p>无论如何,关于调用之间的宏变量发生了什么等问题,你尝试过吗</p>
+ C; k# R- n9 M<ul>
+ E3 P9 \3 [4 G# o) z<li>
' U+ Z. w) B! M/ x$ z( ^在调用执行方法之外按顺序运行宏?
. v/ W2 s8 p6 Q2 b# U% b4 g( h: P</li>. t1 C, I7 x0 m+ P9 ]4 v
<li>
% c/ `/ D  Q1 l在执行之前设置 <wyn>options mprint mlogic symbolgen;</wyn> 以查看日志中的调试信息?, l: h" J1 N2 H$ [8 G
</li>
; d3 R; e+ c  E9 e5 H  x<li>
1 {2 ]3 P8 }8 Y# M4 q( H在您的宏中使用一些 <wyn>%put</wyn> 语句,并在您的 <wyn>call execute</wyn> 数据步中使用 <wyn>put</wyn> 语句,以便查看在各个点生成了什么?9 r( N9 r3 R$ }9 r5 n, W8 ^+ T/ T
</li>
) T/ A& t$ f" z2 K</ul>( ^: [1 f+ C% y. R- U' W
<p>建议在开发宏应用程序时首先让代码运行而不使用宏,然后添加宏变量并显式 <wyn>%let</wyn>-ting 其值,然后在宏的上下文中对其进行测试。之后将移至 <wyn>call execute</wyn>。</p>2 [/ G& l0 I6 k: {+ z
<p>也许尝试以上几点,然后返回一些我们可以调试的日志输出。您发布的代码中还有一些其他错误/问题,但我没有指出它们,而是假设您正在将其缩减为 SO 帖子。</p>1 L) s5 N) A, _4 H
<p>顺便说一句,我喜欢使用 <wyn>data _null_</wyn> 和 <wyn>call execute</wyn> 驱动数据驱动代码的想法,我经常使用这种方法。</p>" N% ]( |- v9 E0 ?; N
<div class="suo-content"><div style="text-align: right;">
! r$ P! A9 i* R' X/ p2 h                <div class="xControl"><i class="fa fa-caret-right"></i>
" ^2 S' U7 F4 h, ]: G* A+ M1 d                        <span class="xTitle"></span># Y& d. D# Z: W' n. W' F
                        相关讨论
1 i7 ^8 E2 K* W+ Q& @- Y) i3 d+ [' a                        <div style="clear: both;"></div>5 P( v# I0 O3 d9 ?" _! Z
                </div>
& [0 m" L4 R/ `: i5 b- s                <div class="xContent" style="display: none;"><p></p>
# u$ o6 V7 X) v/ d# C+ {, g<ul>6 u; F5 I! W" k3 q- Y% m6 h
<li>嗨 sasfrog,我最初确实使用了一个宏,该宏在正常运行宏时起作用,但在调用内部执行</li>5 @  i2 R, @1 r
</ul>
# I' @6 P; a' a  z<p></p></div>
2 v" `. z& W5 J  L& {" C        </div><p></p></div>
: w3 |7 H7 x, m- ?* _: C<hr></div>
回复

使用道具 举报

懒得打字嘛,点击右侧快捷回复 【右侧内容,后台自定义】
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

手机版|飞雪团队

GMT+8, 2025-2-19 06:46 , Processed in 0.072512 second(s), 22 queries , Gzip On.

Powered by Discuz! X3.4

Copyright © 2001-2021, Tencent Cloud.

快速回复 返回顶部 返回列表