BookmarkSubscribeRSS Feed
🔒 This topic is solved and locked. Need further help from the community? Please sign in and ask a new question.
PRAVIN_JAIN
Calcite | Level 5

I have a macro program, inside this macro program there is piece of code which is common across multiple programs. I am trying to call this piece of code by %include statement. But as I use %include it starts giving ERROR: The %DO statement is not valid in open code.

 

Without %INCLUDE it works fine. My understanding is %include gets code from external file into current program so ideally it should work, not sure where getting wrong.

 

Sample Program - 

%macro test();

 

data test1;
set test;
CALL SYMPUT('N',_N_);
CALL SYMPUTX(CAT('CTY',_N_),ctry_code);
run;

 

/*Below DO loop I am putting in external file*/

/*%include "<location>/test_inc.sas";*/

%DO I=1 %TO &N.;

DATA _TMP;
SET dim.&ds.;
where &fld_nm. eq "&&cty&i.";
run;

OPTIONS VALIDVARNAME=UPCASE;

proc export data=_TMP outfile="<location>"
dbms=csv replace;
run;

%END;

 

%mend;

 

%test;

 

 

1 ACCEPTED SOLUTION

Accepted Solutions
Tom
Super User Tom
Super User

You can't do that.  Here is a simplified test case.

filename code temp;
data _null_;
  file code ;
  put '%do i=1 %to &n; put &=i; %end;';
run;

%macro test(n);
 %put &=sysmacroname &=n;
 %include code / source2;
%mend;

%test(1);

The issue is that when %TEST() is compiled it does NOT include the code from the file into the macro definition.  It just puts the %INCLUDE statement into the macro definition.  Therefore when the %INCLUDE runs the macro compiler is not running anymore.  So the code in the include file has to be code that can run as open code.

 

For my simplified solution the fix is to change the %INCLUDE file to define and call its own macro to wrap around the %DO loop.

%macro _code_;
%local i;
%do i=1 %to &n;
  %put &=sysmacroname &=i;
%end;
%mend;
%_code_;

Results:

15    %test(1);
SYSMACRONAME=TEST N=1
NOTE: %INCLUDE (level 1) file CODE is file ....
16   +%macro _code_;
17   +%local i;
18   +%do i=1 %to &n;
19   +  %put &=sysmacroname &=i;
20   +%end;
21   +%mend;
22   +%_code_;
SYSMACRONAME=_CODE_ I=1
MPRINT(TEST):  ;
NOTE: %INCLUDE (level 1) ending.

  

View solution in original post

4 REPLIES 4
PaigeMiller
Diamond | Level 26

Please show us the LOG of both cases, with %include and without %include. We need to see the entire log, all of it, every single line, with nothing chopped out. Please copy the log as text and paste it into the window that appears when you click on the </> icon. DO NOT SKIP THE PART IN RED.

--
Paige Miller
PRAVIN_JAIN
Calcite | Level 5
Failed Log - 
1                                                          The SAS System                              19:52 Sunday, August 29, 2021

1          ;*';*";*/;quit;run;
2          OPTIONS PAGENO=MIN;
3          %LET _CLIENTTASKLABEL='Program (4)';
4          %LET _CLIENTPROCESSFLOWNAME='Process Flow';
5          %LET _CLIENTPROJECTPATH='';
6          %LET _CLIENTPROJECTNAME='';
7          %LET _SASPROGRAMFILE=;
8          
9          ODS _ALL_ CLOSE;
10         OPTIONS DEV=ACTIVEX;
11         GOPTIONS XPIXELS=0 YPIXELS=0;
12         FILENAME EGSR TEMP;
13         ODS tagsets.sasreport13(ID=EGSR) FILE=EGSR
14             STYLE=HtmlBlue
15             STYLESHEET=(URL="file:///C:/Program%20Files/SASHome/SASEnterpriseGuide/7.1/Styles/HtmlBlue.css")
16             NOGTITLE
17             NOGFOOTNOTE
18             GPATH=&sasworklocation
SYMBOLGEN:  Macro variable SASWORKLOCATION resolves to 
            "/localwork2/SAS_work29EB0000FD28_hkpa2ls0136/SAS_work57120000FD28_hkpa2ls0136/"
19             ENCODING=UTF8
20             options(rolap="on")
21         ;
NOTE: Writing TAGSETS.SASREPORT13(EGSR) Body file: EGSR
22         
23         GOPTIONS ACCESSIBLE;
24         options symbolgen mlogic mprint;
25         
26         %MACRO TEST(ds,fld_nm);
27         
28         libname dim "<location>" access =r;
29         
30         proc sql;
31         create table test as
32         select distinct &fld_nm. from dim.&ds.;
33         quit;
34         
35         data test1;
36         set test(WHERE=(&fld_nm. EQ 'IND'));
37         CALL SYMPUT('N',_N_);
38         CALL SYMPUTX(CAT('CTY',_N_),&fld_nm.);
39         run;
40         
41         %PUT &N.;
42         
43         %include "location";
44         
45         %MEND;
46         
47         %test(dim_product,ctry_cde);
MLOGIC(TEST):  Beginning execution.
MLOGIC(TEST):  Parameter DS has value dim_product
MLOGIC(TEST):  Parameter FLD_NM has value ctry_cde
MPRINT(TEST):   libname dim "<location>" access =r;
NOTE: Libref DIM was successfully assigned as follows: 
      Engine:        V9 
      Physical Name: <location>
MPRINT(TEST):   proc sql;
2                                                          The SAS System                              19:52 Sunday, August 29, 2021

SYMBOLGEN:  Macro variable FLD_NM resolves to ctry_cde
SYMBOLGEN:  Macro variable DS resolves to dim_product
MPRINT(TEST):   create table test as select distinct ctry_cde from dim.dim_product;
NOTE: Compression was disabled for data set WORK.TEST because compression overhead would increase the size of the data set.
NOTE: Table WORK.TEST created, with 8 rows and 1 columns.

MPRINT(TEST):   quit;
NOTE: PROCEDURE SQL used (Total process time):
      real time           0.03 seconds
      cpu time            0.01 seconds
      

MPRINT(TEST):   data test1;
SYMBOLGEN:  Macro variable FLD_NM resolves to ctry_cde
MPRINT(TEST):   set test(WHERE=(ctry_cde EQ 'IND'));
MPRINT(TEST):   CALL SYMPUT('N',_N_);
SYMBOLGEN:  Macro variable FLD_NM resolves to ctry_cde
MPRINT(TEST):   CALL SYMPUTX(CAT('CTY',_N_),ctry_cde);
MPRINT(TEST):   run;

NOTE: Numeric values have been converted to character values at the places given by: (Line):(Column).
      3998:233   
NOTE: Compression was disabled for data set WORK.TEST1 because compression overhead would increase the size of the data set.
NOTE: There were 1 observations read from the data set WORK.TEST.
      WHERE ctry_cde='IND';
NOTE: The data set WORK.TEST1 has 1 observations and 1 variables.
NOTE: DATA statement used (Total process time):
      real time           0.01 seconds
      cpu time            0.00 seconds
      

MLOGIC(TEST):  %PUT &N.
SYMBOLGEN:  Macro variable N resolves to            1
1
ERROR: The %DO statement is not valid in open code.
MPRINT(TEST):   DATA _TMP;
SYMBOLGEN:  Macro variable DS resolves to dim_product
MPRINT(TEST):   SET dim.dim_product;
SYMBOLGEN:  Macro variable FLD_NM resolves to ctry_cde
SYMBOLGEN:  && resolves to &.
WARNING: Apparent symbolic reference I not resolved.
SYMBOLGEN:  Unable to resolve the macro variable reference &i
WARNING: Apparent symbolic reference CTY not resolved.
WARNING: Apparent symbolic reference I not resolved.
MPRINT(TEST):   where ctry_cde eq "&cty&i.";
MPRINT(TEST):   run;

NOTE: There were 0 observations read from the data set DIM.DIM_PRODUCT.
      WHERE ctry_cde='&cty&i.';
NOTE: The data set WORK._TMP has 0 observations and 31 variables.
NOTE: DATA statement used (Total process time):
      real time           0.01 seconds
      cpu time            0.02 seconds
      

MPRINT(TEST):   proc print data=_tmp;
MPRINT(TEST):   run;

3                                                          The SAS System                              19:52 Sunday, August 29, 2021

NOTE: No observations in data set WORK._TMP.
NOTE: PROCEDURE PRINT used (Total process time):
      real time           0.00 seconds
      cpu time            0.00 seconds
      

ERROR: The %END statement is not valid in open code.
MLOGIC(TEST):  Ending execution.
60         
61         GOPTIONS NOACCESSIBLE;
62         %LET _CLIENTTASKLABEL=;
63         %LET _CLIENTPROCESSFLOWNAME=;
64         %LET _CLIENTPROJECTPATH=;
65         %LET _CLIENTPROJECTNAME=;
66         %LET _SASPROGRAMFILE=;
67         
68         ;*';*";*/;quit;run;
69         ODS _ALL_ CLOSE;
70         
71         
72         QUIT; RUN;
73         

Success Log (without INCLUDE) - 

NOTE: Writing TAGSETS.SASREPORT13(EGSR) Body file: EGSR
22         
23         GOPTIONS ACCESSIBLE;
24         options symbolgen mlogic mprint;
25         
26         %MACRO TEST(ds,fld_nm);
27         
28         libname dim "<location>" access =r;
29         
30         proc sql;
31         create table test as
32         select distinct &fld_nm. from dim.&ds.;
33         quit;
34         
35         data test1;
36         set test(WHERE=(&fld_nm. EQ 'IND'));
37         CALL SYMPUT('N',_N_);
38         CALL SYMPUTX(CAT('CTY',_N_),&fld_nm.);
39         run;
40         
41         %PUT &N.;
42         /*%PUT &CTY1. &CTY5.;*/
43         
44         /*%include "<location>";*/
45         
46         %DO I=1 %TO &N.;
47         
48         DATA _TMP;
49         SET dim.&ds.;
50         where &fld_nm. eq "&&cty&i.";
51         run;
52         
53         PROC PRINT DATA=_TMP;
54         RUN;
55         
2                                                          The SAS System                              19:52 Sunday, August 29, 2021

56         %END;
57         
58         
59         %MEND;
60         
61         %test(dim_product,ctry_cde);
MLOGIC(TEST):  Beginning execution.
MLOGIC(TEST):  Parameter DS has value dim_product
MLOGIC(TEST):  Parameter FLD_NM has value ctry_cde
MPRINT(TEST):   libname dim “<Location>" access =r;
NOTE: Libref DIM was successfully assigned as follows: 
      Engine:        V9 
      Physical Name: <Location>
MPRINT(TEST):   proc sql;
SYMBOLGEN:  Macro variable FLD_NM resolves to ctry_cde
SYMBOLGEN:  Macro variable DS resolves to dim_product
MPRINT(TEST):   create table test as select distinct ctry_cde from dim.dim_product;
NOTE: Compression was disabled for data set WORK.TEST because compression overhead would increase the size of the data set.
NOTE: Table WORK.TEST created, with 8 rows and 1 columns.

MPRINT(TEST):   quit;
NOTE: PROCEDURE SQL used (Total process time):
      real time           0.03 seconds
      cpu time            0.00 seconds
      

MPRINT(TEST):   data test1;
SYMBOLGEN:  Macro variable FLD_NM resolves to ctry_cde
MPRINT(TEST):   set test(WHERE=(ctry_cde EQ 'IND'));
MPRINT(TEST):   CALL SYMPUT('N',_N_);
SYMBOLGEN:  Macro variable FLD_NM resolves to ctry_cde
MPRINT(TEST):   CALL SYMPUTX(CAT('CTY',_N_),ctry_cde);
MPRINT(TEST):   run;

NOTE: Numeric values have been converted to character values at the places given by: (Line):(Column).
      3651:233   
NOTE: Compression was disabled for data set WORK.TEST1 because compression overhead would increase the size of the data set.
NOTE: There were 1 observations read from the data set WORK.TEST.
      WHERE ctry_cde='IND';
NOTE: The data set WORK.TEST1 has 1 observations and 1 variables.
NOTE: DATA statement used (Total process time):
      real time           0.13 seconds
      cpu time            0.02 seconds
      

MLOGIC(TEST):  %PUT &N.
SYMBOLGEN:  Macro variable N resolves to            1
1
SYMBOLGEN:  Macro variable N resolves to            1
MLOGIC(TEST):  %DO loop beginning; index variable I; start value is 1; stop value is 1; by value is 1.  
MPRINT(TEST):   DATA _TMP;
SYMBOLGEN:  Macro variable DS resolves to dim_product
MPRINT(TEST):   SET dim.dim_product;
SYMBOLGEN:  Macro variable FLD_NM resolves to ctry_cde
SYMBOLGEN:  && resolves to &.
SYMBOLGEN:  Macro variable I resolves to 1
SYMBOLGEN:  Macro variable CTY1 resolves to IND
MPRINT(TEST):   where ctry_cde eq "IND";
3                                                          The SAS System                              19:52 Sunday, August 29, 2021

MPRINT(TEST):   run;

NOTE: There were 55 observations read from the data set DIM.DIM_PRODUCT.
      WHERE ctry_cde='IND';
NOTE: The data set WORK._TMP has 55 observations and 31 variables.
NOTE: Compressing data set WORK._TMP increased size by 100.00 percent. 
      Compressed is 2 pages; un-compressed would require 1 pages.
NOTE: DATA statement used (Total process time):
      real time           0.01 seconds
      cpu time            0.01 seconds
      

MPRINT(TEST):   PROC PRINT DATA=_TMP;
MPRINT(TEST):   RUN;

NOTE: There were 55 observations read from the data set WORK._TMP.
NOTE: PROCEDURE PRINT used (Total process time):
      real time           0.15 seconds
      cpu time            0.16 seconds
      

MLOGIC(TEST):  %DO loop index variable I is now 2; loop will not iterate again.
MLOGIC(TEST):  Ending execution.
PaigeMiller
Diamond | Level 26

Thank you. Please run

options mprint;

and then run the failed code again, modifying the %include code to say %include "location"/source2;

 

Show us the complete log.

 

 

--
Paige Miller
Tom
Super User Tom
Super User

You can't do that.  Here is a simplified test case.

filename code temp;
data _null_;
  file code ;
  put '%do i=1 %to &n; put &=i; %end;';
run;

%macro test(n);
 %put &=sysmacroname &=n;
 %include code / source2;
%mend;

%test(1);

The issue is that when %TEST() is compiled it does NOT include the code from the file into the macro definition.  It just puts the %INCLUDE statement into the macro definition.  Therefore when the %INCLUDE runs the macro compiler is not running anymore.  So the code in the include file has to be code that can run as open code.

 

For my simplified solution the fix is to change the %INCLUDE file to define and call its own macro to wrap around the %DO loop.

%macro _code_;
%local i;
%do i=1 %to &n;
  %put &=sysmacroname &=i;
%end;
%mend;
%_code_;

Results:

15    %test(1);
SYSMACRONAME=TEST N=1
NOTE: %INCLUDE (level 1) file CODE is file ....
16   +%macro _code_;
17   +%local i;
18   +%do i=1 %to &n;
19   +  %put &=sysmacroname &=i;
20   +%end;
21   +%mend;
22   +%_code_;
SYSMACRONAME=_CODE_ I=1
MPRINT(TEST):  ;
NOTE: %INCLUDE (level 1) ending.

  

SAS Innovate 2025: Save the Date

 SAS Innovate 2025 is scheduled for May 6-9 in Orlando, FL. Sign up to be first to learn about the agenda and registration!

Save the date!

How to Concatenate Values

Learn how use the CAT functions in SAS to join values from multiple variables into a single value.

Find more tutorials on the SAS Users YouTube channel.

SAS Training: Just a Click Away

 Ready to level-up your skills? Choose your own adventure.

Browse our catalog!

Discussion stats
  • 4 replies
  • 2759 views
  • 0 likes
  • 3 in conversation