DATA Step, Macro, Functions and more

Reset all %macro before execution

Accepted Solution Solved
Reply
Occasional Contributor
Posts: 16
Accepted Solution

Reset all %macro before execution

Dear expert

     I would like to reset all previously declared %macro so as to avoid macros storing memory variables wrongly to be referred in each SAS program execution.  Should I set OPTIONS MSTORED or NOMSTORED, or specifically set local % in the program.  Thank you for your help.

regards

may


Accepted Solutions
Solution
‎08-14-2017 02:44 PM
SAS Employee
Posts: 340

Re: Reset all %macro before execution

[ Edited ]

Editor's note: Many great solutions mentioned but to properly delete a macro variable you would use %SYMDEL and to properly remove a macro compiled to the WORK catalog you would use %SYSMACDELETE as metioned by gergely_batho .

 

See also:

%SYSMACDELETE;

%SYSMSTORECLEAR;

View solution in original post


All Replies
Frequent Contributor
Posts: 117

Re: Reset all %macro before execution

Hi,

Use NOMSTORED option not to store the variables.

Occasional Contributor
Posts: 8

Re: Reset all %macro before execution

Hi ,

Use the Macro statement :

%SYMDEL macro-variable-1 <...macro-variable-n></option> ;

Regards.

Occasional Contributor
Posts: 16

Re: Reset all %macro before execution

Suppose I have macros, say

  %macro test_1;

      x=123;

  %mend test_1;

or

  %let test_2=123;

Should I write the syntax at the very begining in the program to delete such macros before SAS execution :

  %SYMDEL test_1 test_2 /nowarn;

Please help.

regards

may

Super User
Super User
Posts: 7,942

Re: Reset all %macro before execution

Hi,

The sydel command will only delete macro variables, not macros themselves.  So in your example, %symdel test2 / nowarn;  would be fine, but you can't use that for test_1.  As for the macro code, well, this really is all down to organization, and is my biggest gripe with the macro system.  I would suggest be explicit in which macro code you are including, too often I see:

File a:

%macro test;

     data a;

          aaa="Hello";

     run;

%mend test;

File b:

%macro test;

     data a;

          aaa="World";

     run;

%mend test;

File c:

%include file_a;

%do_something;

%test; /* AAA is Hello */

%include_another_program;  /* This has the line %include file_b */

%test;  /* AAA is World */

And debugging means trawling through layers of include statements, macro defs, scope etc.  For some coding you can use call execute to generate code at run-time, hence avoiding using macro variables/macros at all.  Otherwise its really up to you to ensure your macro call is correct.

Occasional Contributor
Posts: 16

Re: Reset all %macro before execution

Most of the time we write so many macros %LET and %include within the programs and forget how many of them have been stated.  I simply quit SAS and invoke again in order to refresh all macro settings before execution.  Could anyone tell me the simpliest way to handle this ?  Thank you.

regards

may

Super User
Super User
Posts: 7,942

Re: Reset all %macro before execution

Yep, follow good programming guidance / structured programming.  E.g. declare macro variables either at the start of the program, for global ones, or within their scope for local ones.  Store macros with guidance documentation in a protected library area, so you can ensure the ones you use are validated ones.  Many other things can help organize the code and make it more readable/maintainable and their are several website dedicated to this topic although this type of thing doesn't seem to have come to SAS programming that much as yet:

Wikipedia definition: http://en.wikipedia.org/wiki/Best_Coding_Practices

You could also run your programs in batch mode, this means tha SAS would startup, run your program, then close - hence not keeping over anything from previous runs.  Other than that I don't think there is a (at least simple) way of cleaning you SAS run.

Respected Advisor
Posts: 4,173

Re: Reset all %macro before execution

Start a new SAS session and run below code. This might give you an idea how many macros are already pre-compiled and waiting for you without you having run explicitly a single line of code.

The same is true if you then execute a "%put _all_;" as the very first command.

So: To not use macros & macro variable values in a wrong version or state is mainly about clean program design. If I develop in EG then one of my last tests is always running the program after spawning a new session (disconnect/reconnect to the server). And if it's serious code then I run it also in batch-mode.

%macro test;

  %put I exist;

%mend;

/** list catalogs in a specific library **/

proc datasets library=work memtype=catalog;

quit;

/** list all macros in all libraries and catalogs **/

proc sql;

  select *

  from dictionary.catalogs

  where memtype='CATALOG' and objtype='MACRO'

  ;

quit;

/** delete a macro in a catalog **/

proc catalog cat=work.sasmac1;

  contents;

  run;

  delete test / entrytype=macro;

  run;

  contents;

  run;

quit;

Occasional Contributor
Posts: 6

Re: Reset all %macro before execution

This thread basically illustrates a huge amount of confusion about macros.

1) Macro design is key

2) The process of writing macros involves isolating the VALUES from the PROCESS. The macro abstracts the process. You supply the variables in 2 ways:

a) Using %LET

b) Passing values in as arguments and defining the macro variables as parameters

So, if you have

%let dset=a;

%let iv=a b c d e;

proc reg data=&dset;

model dv=&iv;

run;

This should be rewritten, and the %let statements ELIMINATED. Write

%macro runreg(dset=,iv=);

proc reg data=&dset;

model dv=&iv;

run;

%mend runreg;

%runreg(dset=a,iv=a b c d e)

This AUTOMATICALLY resets the macro variables, because they are defined in the macro call.

Super User
Super User
Posts: 7,039

Re: Reset all %macro before execution

Best is to just start a new SAS session.

How to remove previously compiled macros definitions depends partly on how you are storing your compiled macros.  If you are just using basic SAS defaults then the compiled macros will be in the WORK catalog named SASMACR.  But with older versions of Enterprise Guide I did notice that it also seemed to create a catalog named SASMAC1.

proc catalog c=work.sasmacr force kill;

quit;


You also might want to remove any previously compiled formats from WORK.FORMATS.

proc catalog c=work.formats force kill;

quit;

Respected Advisor
Posts: 4,173

Re: Reset all %macro before execution

It's SASMAC1 for me using EG6.1 with SAS9.4 under Win7 64bit

Solution
‎08-14-2017 02:44 PM
SAS Employee
Posts: 340

Re: Reset all %macro before execution

[ Edited ]

Editor's note: Many great solutions mentioned but to properly delete a macro variable you would use %SYMDEL and to properly remove a macro compiled to the WORK catalog you would use %SYSMACDELETE as metioned by gergely_batho .

 

See also:

%SYSMACDELETE;

%SYSMSTORECLEAR;

PROC Star
Posts: 1,322

Re: Reset all %macro before execution

For macro variables, I use:

data _null_;

  set sashelp.vmacro;

  where scope='GLOBAL' and offset=0 and name not like "SYS%" and name not like "AF%"; 

  call execute('%nrstr(%%)symdel '||trim(left(name))||';');

run;

*Set variables that start with SYS or AF to null, since we cant delete them;

*Oddly, macro variable SYS_SQL_IP_ALL (created by PROC SQL) stores a dot when it is set to null.;

data _null_;

  set sashelp.vmacro;

  where scope='GLOBAL' and offset=0 and (name like "SYS%" or name like "AF%"); 

  call execute('%nrstr(%%)let '||trim(left(name))||'=;');

run;

For macros I use Tom's PROC CATALOG approach.   Of course there is lots more you may want to clear if you spend a day or more in an interactive SAS session (work datasetsets, templates, format catalogs, titles, etc etc).

I mostly use that in interactive PC SAS.  Sometimes EG doesn't like it when I delete everything, because it relies on some macro variables and even some work datasets for its own use.

And whether EG or PC SAS, keep in mind that interactive sessions should just be for development (IMHO), even if you have a nice %CleanSession() macro.  Production runs should be done in batch.

HTH,

--Q.

Occasional Contributor
Posts: 16

Re: Reset all %macro before execution

It's so great !  Thank you all of you.

may

🔒 This topic is solved and locked.

Need further help from the community? Please ask a new question.

Discussion stats
  • 13 replies
  • 10502 views
  • 1 like
  • 9 in conversation