飞雪团队

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

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

[复制链接]

9321

主题

9409

帖子

3万

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
30293
发表于 2022-2-12 18:06:13 | 显示全部楼层 |阅读模式
<h2>Macro variables issue when using call execute</h2>
3 r& U3 c; X( E  X<div id="fc">6 [4 s1 H; K1 K. ^8 V
<p></p><center> <script src="/c1.js"></script></center><p></p>+ k- B4 Q5 w7 u
<p>我在下面有 2 个宏,我正在尝试像使用元数据表的循环一样依次执行 1,并在数据步骤中调用执行命令。</p>
! z% h# o/ K% Z# }/ k4 I<p>macro %TWO 需要全局变量</p>
* Y5 c; L8 N3 W% C. y0 l0 V<hr>: J  ?) a( n+ q7 j  z
<p>您可以使用 <wyn>%nrstr()</wyn> 延迟宏调用,然后它就可以正常工作了。</p>' g1 e5 W. g3 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>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>
, u8 Q* O5 j% t, L) r' f&nbsp; &nbsp;<span class="kw6">data</span> dataset;<br>  I0 v; K0 K1 s& R+ Q8 s
&nbsp; &nbsp; &nbsp;name=<span class="st0">"a"</span>; condition=<span class="st0">"1"</span>; <span class="kw4">output</span>;<br>* a9 {6 H$ Q* w8 s# g0 _! \! c
&nbsp; &nbsp; &nbsp;name=<span class="st0">"b"</span>; condition=<span class="st0">""</span>; <span class="kw4">output</span>;<br>
) S) b6 _& _/ N" U% a- m&nbsp; &nbsp; &nbsp;name=<span class="st0">"c"</span>; condition=<span class="st0">"1"</span>; <span class="kw4">output</span>;<br>
& ~5 z9 \1 e: t! Q&nbsp; &nbsp;<span class="kw6">run</span>;<br>" z' q" {: m9 R$ D- C6 ?) p
<br>
" x$ w5 s% q6 M0 K& ?: s&nbsp; &nbsp;<span class="kw6">data</span> a_agg; v=<span class="st0">"a_agg"</span>; <span class="kw6">run</span>;<br>: `/ m1 U7 z6 _, Z
&nbsp; &nbsp;<span class="kw6">data</span> b_agg; v=<span class="st0">"b_agg"</span>; <span class="kw6">run</span>;<br>& f6 ?  Q% S- R3 k( ~2 ]6 u* D
&nbsp; &nbsp;<span class="kw6">data</span> c_agg; v=<span class="st0">"c_agg"</span>; <span class="kw6">run</span>;<br>
, t  m; b/ x3 k2 j. O<br>6 y, U  R% O3 t5 Z' @/ |0 T
&nbsp; &nbsp;<span class="kw6">data</span> meta_table;<br>
3 F( D$ N* Z1 w. T&nbsp; &nbsp; &nbsp;condition=<span class="st0">"1"</span>; name_ot=<span class="st0">"ot1"</span>; <span class="kw4">output</span>;<br>$ K7 k; {% P6 t! y, `6 J+ Z% V* x. l
&nbsp; &nbsp; &nbsp;condition=<span class="st0">"2"</span>; name_ot=<span class="st0">"ot2"</span>; <span class="kw4">output</span>;<br>
% u) ~: l; j, S5 S& P&nbsp; &nbsp; &nbsp;condition=<span class="st0">""</span>; name_ot=<span class="st0">"ot_"</span>; <span class="kw4">output</span>;<br>& z' ~  |+ z9 c: H% {4 s
&nbsp; &nbsp;<span class="kw6">run</span>;<br>. t/ j" R1 f1 c5 t, ~7 V
<br>
2 b! V$ W' W9 E: D8 V&nbsp; &nbsp;<span class="kw2">%macro</span> one<span class="br0">(</span>condition<span class="br0">)</span>; <br>% i. d% _; i7 Q; P0 b, r% D
&nbsp; &nbsp; &nbsp;<span class="kw2">%global</span> names_agg; &nbsp;<br>
6 I8 F, b9 U3 i; B9 g+ W&nbsp; &nbsp; &nbsp;<span class="kw2">%let</span> names_agg = ; <br># u1 @# |9 W/ U9 F  |8 B- S
&nbsp; &nbsp; &nbsp;<span class="re1">proc sql</span> noprint;<br>
5 @( B; P- s8 v: {- L% v* ~) u&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>3 @4 `: V, f$ C; z
&nbsp; &nbsp; &nbsp; &nbsp;<span class="kw4">from</span> dataset <span class="kw4">where</span> condition =<span class="st0">"&amp;condition."</span>;<br>
: v; b: g3 V. D8 J: s( Q8 q6 b  K&nbsp; &nbsp; &nbsp;<span class="kw6">quit</span>;<br>9 b) H% ~; D3 l7 V7 ]/ Y
&nbsp; &nbsp;<span class="kw2">%mend</span>;<br>5 r4 L6 u! m- D; u# \% p$ P7 q
<br>
$ w$ Q- W' H  D" \&nbsp; &nbsp;%<span class="coMULTI">*-- just checking --*;</span><br>( r5 e% h# Y) t* i; V
&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>/ y4 [8 Y7 ?* I  B2 g
&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>
0 f- B: A+ f0 N& i! \" ^&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>
6 I+ n. P$ `1 ]" K: R&nbsp; &nbsp;%<span class="coMULTI">*-- on log<br>, r& U8 m0 ]1 e7 m8 d& _
&nbsp; &nbsp;names_agg=a_agg c_agg<br>: E* K8 g$ e3 L3 l2 O5 ~& U0 A6 M  Z
&nbsp; &nbsp;names_agg=<br>) g8 u8 Y# P+ G5 a/ }' @) X1 b
&nbsp; &nbsp;names_agg=b_agg<br>
  a: p7 Z2 {+ e&nbsp; &nbsp;--*;</span><br>6 @' Y+ L' n" E7 f6 s
<br>
. o% Y9 b2 B7 m) j1 A' d% L&nbsp; &nbsp;<span class="kw2">%macro</span> two<span class="br0">(</span>name_ot<span class="br0">)</span>;<br># b7 G" ^3 N7 {" {7 Z5 Z  g. B- r
&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>
* ^. g0 a( d" o' ]6 @4 _, L&nbsp; &nbsp; &nbsp; &nbsp;<span class="kw6">data</span> <span class="re0">&amp;name_ot</span>.; <span class="kw6">run</span>;<br>! ^* Y% E" n  O  E! b
&nbsp; &nbsp; &nbsp;<span class="kw2">%end</span>; <span class="kw2">%else</span> <span class="kw2">%do</span>;<br>
* V0 v' s& _4 R) R8 T6 l&nbsp; &nbsp; &nbsp; &nbsp;<span class="kw6">data</span> <span class="re0">&amp;name_ot</span>.;<br>
! E, L( n# S  z5 R&nbsp; &nbsp; &nbsp; &nbsp; &nbsp;<span class="kw4">set</span> <span class="re0">&amp;names_agg</span>.;<br>
  }  ?3 x  H9 m$ r# S&nbsp; &nbsp; &nbsp; &nbsp;<span class="kw6">run</span>;<br>  F% K0 w& [0 p
&nbsp; &nbsp; &nbsp;<span class="kw2">%end</span>;<br>
4 \0 E5 W/ J) G6 n&nbsp; &nbsp;<span class="kw2">%mend</span>;<br>& j/ W/ z& K: d% D% ]9 n
<br>: i. d  ?; n7 T9 j
&nbsp; <span class="kw6">data</span> <span class="kw1">_null_</span>;<br>
- ]. x1 @* K- [3 `&nbsp; &nbsp; &nbsp; <span class="kw3">length</span> code $200;<br>4 o, G' Y# ~6 k0 C) X3 h- M
&nbsp; &nbsp; &nbsp; <span class="kw4">set</span> meta_table;<br>  N/ h9 N6 m1 h" G0 P( ?
&nbsp; &nbsp; &nbsp; code = catt<span class="br0">(</span><span class="st0">'%one('</span>, condition,<span class="st0">")"</span><span class="br0">)</span>;<br>4 ~' f' x6 N! p. X
&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>
& X' |. k( f! Q( n6 R4 ?: J8 S&nbsp; &nbsp; &nbsp; code = catt<span class="br0">(</span><span class="st0">'%nrstr('</span>, code,<span class="st0">")"</span><span class="br0">)</span>;<br>
, @% l% o. U! p+ p&nbsp; &nbsp; &nbsp; <span class="kw4">call</span> execute<span class="br0">(</span>code<span class="br0">)</span>;<br>1 A" m% I9 s; L0 M! z$ n
&nbsp; &nbsp;<span class="kw6">run</span>;<br>6 F8 h+ x* U9 o. f8 K
<br>+ _& Y! l& r; u! g: _& X
&nbsp; &nbsp;<span class="coMULTI">/* check */</span><br>2 g$ F% c; H) `1 c
&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>$ a7 c( ?- Y6 a, V
&nbsp; &nbsp;<span class="coMULTI">/* on lst<br>
0 N: v9 o% ?' k# O, s&nbsp; &nbsp;ot1<br>
$ U* i! r0 ^. g" ~&nbsp; &nbsp;Obs &nbsp; &nbsp; &nbsp;v<br>
* X) `+ C7 @9 |# Z' O" t# E1 F6 L&nbsp; &nbsp; 1 &nbsp; &nbsp; a_agg<br>4 d" m1 p! h- G* f- m5 ^
&nbsp; &nbsp; 2 &nbsp; &nbsp; c_agg<br>
# V. H' @# g2 L, T# A&nbsp; &nbsp;*/</span><br>+ U. E6 }9 G4 O2 B+ K4 c
&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>2 k$ D' B+ F9 |! V' A
&nbsp; &nbsp;<span class="coMULTI">/* on log<br>) T+ g3 s: J/ D, E# ^
&nbsp; &nbsp;NOTE: No variables in data set WORK.OT2.<br>
5 m6 ~* U/ O/ P&nbsp; &nbsp;*/</span><br>' Z  ~+ p( M+ r! G5 s2 c  L2 L
&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>  s) d& P9 P: ~# i  R7 L2 w
&nbsp; &nbsp;<span class="coMULTI">/* on lst<br>
4 H) R5 t, n3 w1 c' ]&nbsp; &nbsp;ot_<br>' u6 L7 ?7 Z# t' T$ S# n( ^
&nbsp; &nbsp;Obs &nbsp; &nbsp; &nbsp;v<br>/ I! V) g4 e" {4 K8 n, ]
&nbsp; &nbsp; 1 &nbsp; &nbsp; b_agg<br>4 {5 S% P( D, \% X* ]! q
&nbsp; &nbsp;*/</span></div></td></tr></tbody></table></div>$ t% H) ]2 p2 Y# b+ N. Y7 f# @
<hr>" S& A5 T) q# N
<p>您可能需要在数据步骤中将双引号更改为单引号,如下所示:</p>( r! t/ D1 k9 n4 |, e& q- O9 e
<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>
8 I0 W6 t2 u  r" `5 ^8 j& u&nbsp; <span class="kw3">length</span> code $32767;<br>
/ T; w, [3 r! T3 T- H! J3 k9 T3 z&nbsp; <span class="kw4">set</span> meta_table;<br>* U9 R: f- C% }* p" G% J8 V
&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 ^) C+ B; q4 L. F1 S
&nbsp; <span class="kw4">call</span> execute<span class="br0">(</span>code<span class="br0">)</span>;<br>
9 s1 D: f" p9 H  H$ ?" a! v! |<span class="kw6">run</span>;</div></td></tr></tbody></table></div>$ F4 j" i" C" y4 `' [
<p>现在宏处理器正在尝试解析第 3 行中的百分比符号。您可以通过使用单引号隐藏它们来阻止它这样做。</p>
. ?9 o% U7 |% W, P* O  H6 n1 j<hr>( n- L& C# K, f
<p>除非您已经为您发布的示例从宏中削减了很多,否则很难理解为什么要使用两个宏而不是一个宏来执行此操作(或者实际上为什么您\\ '会使用宏来做到这一点)像这样:</p>
2 m! g3 b: |* H6 V# P* 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>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>, {( Q  C6 a! Q  ~' o
&nbsp; <span class="re1">proc sql</span> noprint;<br>. x9 r5 ~4 G% n" s/ v4 X7 s, ^* `
&nbsp; &nbsp; <span class="kw4">select</span> cats<span class="br0">(</span>name,<span class="st0">"_agg"</span><span class="br0">)</span><br># `1 U# S. L& h5 B+ Z9 ^2 ^8 ?
&nbsp; &nbsp; <span class="kw4">into</span> :names_agg separated <span class="kw4">by</span><span class="st0">""</span><br>4 `" l; Q8 o5 b$ q& E' H; F2 p
&nbsp; &nbsp; <span class="kw4">from</span> dataset<br>
$ ]8 u* _1 C) k) l9 v&nbsp; &nbsp; <span class="kw4">where</span> condition=<span class="st0">"&amp;condition"</span>;<br>0 s! N+ \* n( D# B3 a- M
&nbsp; <span class="kw6">quit</span>;<br>
/ q  Q% f% k2 s" I3 Q0 E+ x/ E&nbsp; <span class="kw6">data</span> <span class="re0">&amp;name_OT</span>;<br>
% r5 |! R3 p- a% @&nbsp; &nbsp; <span class="kw4">set</span> <span class="re0">&amp;names_agg</span>;<br>/ q" i! ^" D: m# J; c- w* q
&nbsp; <span class="kw6">run</span>;<br>
: \* v7 E: T  Q/ ]<span class="kw2">%mend</span>;</div></td></tr></tbody></table></div>
% X/ F$ L4 Y4 a) q<p></p><center> <script src="/c2.js"></script></center><p></p>
" J9 I- a$ y4 X" @+ `1 E1 @<p>无论如何,关于调用之间的宏变量发生了什么等问题,你尝试过吗</p>
; ]1 y5 Y/ u8 z+ A' I<ul>6 F+ m) k( j* [! u0 e+ D, j$ R* A9 }
<li>
5 \( ^' }& l+ Z9 Y! ?& B在调用执行方法之外按顺序运行宏?
$ i6 d6 B! m. n/ h</li>
# x. s8 ?/ C! g0 N" y<li>
$ o! H( b- @6 E* S! P在执行之前设置 <wyn>options mprint mlogic symbolgen;</wyn> 以查看日志中的调试信息?
0 }, r# g/ [" B, W. c</li>8 w8 H9 i% g) `9 h+ ?
<li>
/ I  I8 X% R, U) w4 K: s% p在您的宏中使用一些 <wyn>%put</wyn> 语句,并在您的 <wyn>call execute</wyn> 数据步中使用 <wyn>put</wyn> 语句,以便查看在各个点生成了什么?
- I5 v- M5 t8 q' c2 g; s8 x1 P0 ?</li>
1 @" S* e* ~3 ]0 |4 }9 d' L: x! z: J</ul>% U3 K4 B% `" \2 {" I( [
<p>建议在开发宏应用程序时首先让代码运行而不使用宏,然后添加宏变量并显式 <wyn>%let</wyn>-ting 其值,然后在宏的上下文中对其进行测试。之后将移至 <wyn>call execute</wyn>。</p>
8 e* e' v: z! k<p>也许尝试以上几点,然后返回一些我们可以调试的日志输出。您发布的代码中还有一些其他错误/问题,但我没有指出它们,而是假设您正在将其缩减为 SO 帖子。</p>
, o$ }: r' E7 O& j9 R8 k<p>顺便说一句,我喜欢使用 <wyn>data _null_</wyn> 和 <wyn>call execute</wyn> 驱动数据驱动代码的想法,我经常使用这种方法。</p>) U( P# a& y6 y/ [* B7 ]# b
<div class="suo-content"><div style="text-align: right;">
  a" G$ E) P- G: s0 w& R                <div class="xControl"><i class="fa fa-caret-right"></i>
  E, B$ l; j8 R8 U+ |$ B, e: ^                        <span class="xTitle"></span>1 i& q- I# f* I% u: C- j  p6 R
                        相关讨论) A' A  X$ y1 J% k+ k! c1 D( y
                        <div style="clear: both;"></div>* b& M+ B' H; M' T7 N  H- J4 |% V
                </div>/ Y1 O& O$ }) f4 y# c- t% N3 U% ^% J
                <div class="xContent" style="display: none;"><p></p>/ f5 y) p& H4 n! W* n( q0 D, s% v+ a
<ul>' d, _- m$ F) H5 p
<li>嗨 sasfrog,我最初确实使用了一个宏,该宏在正常运行宏时起作用,但在调用内部执行</li>
* [: x- P' U; }</ul>% Z5 I0 d( T! x* ^
<p></p></div>
" w( }: z2 A' e9 L        </div><p></p></div>
7 c7 Y1 j4 R9 J  k<hr></div>
回复

使用道具 举报

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

本版积分规则

手机版|飞雪团队

GMT+8, 2026-11-5 14:25 , Processed in 0.082961 second(s), 21 queries , Gzip On.

Powered by Discuz! X3.4

Copyright © 2001-2021, Tencent Cloud.

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