Hi @andreas_lds , @Shmuel , another question is about the ERROR existing when running the macro called "All positional parameters must precede keyword parameters", could you please tell me how to sort it out?
Here is my code:
options compress=yes reuse=yes;
%macro ImportAndTranspose(
File=
, StartSheet=
, EndSheet=
);
%local i;
%do i = &StartSheet. %to &EndSheet.;
%if &i=1 %then %do;
proc import datafile= "&File."
out= sheet1
dbms= xlsx
replace;
range= "Sheet1$A:X";
getnames= yes;
run;
proc sort data= sheet1;
by Type;
run;
%end;
%else %if &i= &EndSheet. %then %do;
proc import datafile= "&File."
out= sheet&i.
dbms= xlsx
replace;
range= "Sheet&i.$A:AG";
getnames= yes;
run;
proc sort data= sheet&i.;
by Type;
run;
proc transpose data= sheet&i.
out= sheet&i._out(rename=(COL1=s&i. _NAME_=Year) drop=_label_);
by Type;
VAR '1988'N - '2019'N;
run;
proc print data=sheet&i._out;
run;
data sheet&i._outx;
set sheet&i._out;
if s&i. in: ('NA', '$$') then s&i. =".";
run;
%end;
%else %if (&i ne 1) and (&i ne Endsheet.) %then %do;
proc import datafile= "&File."
out= sheet&i.
dbms= xlsx
replace;
range= "Sheet&i.$A:AG";
getnames= yes;
run;
proc sort data= sheet&i.;
by Type;
run;
proc transpose data= sheet&i.
out= sheet&i._out(rename=(COL1=s&i. _NAME_=Year) drop=_label_);
by Type;
VAR '1988'N - '2019'N;
run;
proc print data=sheet&i._out;
run;
DATA sheet&i._outx;
set sheet&i._out;
if s&i. not in: ('NA', '$$') then s&i.2=input(s&i., 32.);
drop s&i.;
run;
%end;
%end;
%mend;
*Replicate all file in one folder;
data _null_;
length fref $8 fname $200;
did = filename(fref,'C:\Users\pnguyen\Desktop\New folder');
did = dopen(fref);
do i = 1 to dnum(did);
fname = dread(did,i);
cmd=catx(',', '%ImportAndTranspose(File=',
strip(fname), 'startsheet=1,endsheet=34);');
call execute(cmd);
end;
did = dclose(did);
did = filename(fref);
keep fname;
run;
The log is as below:
1 The SAS System 14:42 Sunday, January 3, 2021
1 ;*';*";*/;quit;run;
2 OPTIONS PAGENO=MIN;
3 %LET _CLIENTTASKLABEL='replicate code for all sheets -included s34 _inc filenamer';
4 %LET _CLIENTPROCESSFLOWNAME='Process Flow';
5 %LET _CLIENTPROJECTPATH='C:\Users\pnguyen\OneDrive - Massey University\SAS\29_Dec_redo_all.egp';
6 %LET _CLIENTPROJECTPATHHOST='IT082760';
7 %LET _CLIENTPROJECTNAME='29_Dec_redo_all.egp';
8 %LET _SASPROGRAMFILE='';
9 %LET _SASPROGRAMFILEHOST='';
10
11 ODS _ALL_ CLOSE;
12 OPTIONS DEV=SVG;
13 GOPTIONS XPIXELS=0 YPIXELS=0;
14 %macro HTML5AccessibleGraphSupported;
15 %if %_SAS_VERCOMP_FV(9,4,4, 0,0,0) >= 0 %then ACCESSIBLE_GRAPH;
16 %mend;
17 FILENAME EGHTML TEMP;
18 ODS HTML5(ID=EGHTML) FILE=EGHTML
19 OPTIONS(BITMAP_MODE='INLINE')
20 %HTML5AccessibleGraphSupported
21 ENCODING='utf-8'
22 STYLE=HtmlBlue
23 NOGTITLE
24 NOGFOOTNOTE
25 GPATH=&sasworklocation
26 ;
NOTE: Writing HTML5(EGHTML) Body file: EGHTML
27
28 options compress=yes reuse=yes;
29
30 %macro ImportAndTranspose(
31 File=
32 , StartSheet=
33 , EndSheet=
34 );
35
36 %local i;
37
38 %do i = &StartSheet. %to &EndSheet.;
39
40 %if &i=1 %then %do;
41
42 proc import datafile= "&File."
43 out= sheet1
44 dbms= xlsx
45 replace;
46 range= "Sheet1$A:X";
47 getnames= yes;
48 run;
49
50 proc sort data= sheet1;
51 by Type;
52 run;
53 %end;
54
55 %else %if &i= &EndSheet. %then %do;
56 proc import datafile= "&File."
57 out= sheet&i.
2 The SAS System 14:42 Sunday, January 3, 2021
58 dbms= xlsx
59 replace;
60 range= "Sheet&i.$A:AG";
61 getnames= yes;
62 run;
63
64 proc sort data= sheet&i.;
65 by Type;
66 run;
67
68 proc transpose data= sheet&i.
69 out= sheet&i._out(rename=(COL1=s&i. _NAME_=Year) drop=_label_);
70 by Type;
71 VAR '1988'N - '2019'N;
72 run;
73 proc print data=sheet&i._out;
74 run;
75
76 data sheet&i._outx;
77 set sheet&i._out;
78 if s&i. in: ('NA', '$$') then s&i. =".";
79 run;
80
81 %end;
82
83
84 %else %if (&i ne 1) and (&i ne Endsheet.) %then %do;
85 proc import datafile= "&File."
86 out= sheet&i.
87 dbms= xlsx
88 replace;
89 range= "Sheet&i.$A:AG";
90 getnames= yes;
91 run;
92
93 proc sort data= sheet&i.;
94 by Type;
95 run;
96
97 proc transpose data= sheet&i.
98 out= sheet&i._out(rename=(COL1=s&i. _NAME_=Year) drop=_label_);
99 by Type;
100 VAR '1988'N - '2019'N;
101 run;
102 proc print data=sheet&i._out;
103 run;
104
105 DATA sheet&i._outx;
106 set sheet&i._out;
107
108 if s&i. not in: ('NA', '$$') then s&i.2=input(s&i., 32.);
109 drop s&i.;
110 run;
111 %end;
112
113
114
115 %end;
3 The SAS System 14:42 Sunday, January 3, 2021
116
117 %mend;
118
119 *Replicate all file in one folder;
120 data _null_;
121 length fref $8 fname $200;
122 did = filename(fref,'C:\Users\pnguyen\Desktop\New folder');
123 did = dopen(fref);
124 do i = 1 to dnum(did);
125 fname = dread(did,i);
126 cmd=catx(',', '%ImportAndTranspose(File=',
127 strip(fname), 'startsheet=1,endsheet=34);');
128 call execute(cmd);
129 end;
130 did = dclose(did);
131 did = filename(fref);
132 keep fname;
133 run;
ERROR: All positional parameters must precede keyword parameters.
ERROR: All positional parameters must precede keyword parameters.
ERROR: All positional parameters must precede keyword parameters.
NOTE: The SAS System stopped processing this step because of errors.
NOTE: DATA statement used (Total process time):
real time 0.00 seconds
cpu time 0.00 seconds
NOTE: CALL EXECUTE generated line.
NOTE: Line generated by the CALL EXECUTE routine.
1 +startsheet=1,endsheet=34);
__________
180
ERROR 180-322: Statement is not valid or it is used out of proper order.
NOTE: Line generated by the CALL EXECUTE routine.
2 +startsheet=1,endsheet=34);
__________
180
ERROR 180-322: Statement is not valid or it is used out of proper order.
NOTE: Line generated by the CALL EXECUTE routine.
3 +startsheet=1,endsheet=34);
__________
180
ERROR 180-322: Statement is not valid or it is used out of proper order.
134
135 %LET _CLIENTTASKLABEL=;
136 %LET _CLIENTPROCESSFLOWNAME=;
137 %LET _CLIENTPROJECTPATH=;
138 %LET _CLIENTPROJECTPATHHOST=;
139 %LET _CLIENTPROJECTNAME=;
140 %LET _SASPROGRAMFILE=;
141 %LET _SASPROGRAMFILEHOST=;
4 The SAS System 14:42 Sunday, January 3, 2021
142
143 ;*';*";*/;quit;run;
144 ODS _ALL_ CLOSE;
145
146
147 QUIT; RUN;
148
While I run the code of reading all filenames only, the code work successfully:
data filenames;
length fref $8 fname $200;
did = filename(fref,'H:\');
did = dopen(fref);
do i = 1 to dnum(did);
fname = dread(did,i);
output;
end;
did = dclose(did);
did = filename(fref);
keep fname;
run;
So I thought the problem occurring due to the added function called (execute) or else.
Many thanks and cheers!
@Phil_NZ - I've tweaked your command string - hopefully that will work better. If not add a - put cmd = ; - statement to check the syntax:
data _null_;
length fref $8 fname $200;
did = filename(fref,'C:\Users\pnguyen\Desktop\New folder');
did = dopen(fref);
do i = 1 to dnum(did);
fname = dread(did,i);
cmd=cats(%ImportAndTranspose(File=',
strip(fname), ', startsheet=1, endsheet=34);');
call execute(cmd);
end;
did = dclose(did);
did = filename(fref);
keep fname;
run;
Thank you very much for your help, @SASKiwi .
It seems that I no longer face the same problem, but also raising some other errors, I am wondering what is the problem there.
Here is the log:
43 options compress=yes reuse=yes;
44
45 %macro ImportAndTranspose(
46 File=
47 , StartSheet=
48 , EndSheet=
49 );
50
51 %local i;
52
53 %do i = &StartSheet. %to &EndSheet.;
54
55 %if &i=1 %then %do;
56
57 proc import datafile= "&File."
2 The SAS System 14:42 Sunday, January 3, 2021
58 out= sheet1
59 dbms= xlsx
60 replace;
61 range= "Sheet1$A:X";
62 getnames= yes;
63 run;
64
65 proc sort data= sheet1;
66 by Type;
67 run;
68 %end;
69
70 %else %if &i= &EndSheet. %then %do;
71 proc import datafile= "&File."
72 out= sheet&i.
73 dbms= xlsx
74 replace;
75 range= "Sheet&i.$A:AG";
76 getnames= yes;
77 run;
78
79 proc sort data= sheet&i.;
80 by Type;
81 run;
82
83 proc transpose data= sheet&i.
84 out= sheet&i._out(rename=(COL1=s&i. _NAME_=Year) drop=_label_);
85 by Type;
86 VAR '1988'N - '2019'N;
87 run;
88 proc print data=sheet&i._out;
89 run;
90
91 data sheet&i._outx;
92 set sheet&i._out;
93 if s&i. in: ('NA', '$$') then s&i. =".";
94 run;
95
96 %end;
97
98
99 %else %if (&i ne 1) and (&i ne Endsheet.) %then %do;
100 proc import datafile= "&File."
101 out= sheet&i.
102 dbms= xlsx
103 replace;
104 range= "Sheet&i.$A:AG";
105 getnames= yes;
106 run;
107
108 proc sort data= sheet&i.;
109 by Type;
110 run;
111
112 proc transpose data= sheet&i.
113 out= sheet&i._out(rename=(COL1=s&i. _NAME_=Year) drop=_label_);
114 by Type;
115 VAR '1988'N - '2019'N;
3 The SAS System 14:42 Sunday, January 3, 2021
116 run;
117 proc print data=sheet&i._out;
118 run;
119
120 DATA sheet&i._outx;
121 set sheet&i._out;
122
123 if s&i. not in: ('NA', '$$') then s&i.2=input(s&i., 32.);
124 drop s&i.;
125 run;
126 %end;
127
128
129
130 %end;
131
132 %mend;
133
134 *Replicate all file in one folder;
135 data _null_;
136 length fref $8 fname $200;
137 did = filename(fref,'C:\Users\pnguyen\Desktop\New folder');
138 did = dopen(fref);
139 do i = 1 to dnum(did);
140 fname = dread(did,i);
141 cmd=cats(%ImportAndTranspose(File=',
142 strip(fname),',startsheet=1,endsheet=34);');
NOTE: Line generated by the invoked macro "IMPORTANDTRANSPOSE".
142 proc import datafile= "&File." out= sheet1 dbms= xlsx replace;
______ ___ _______
388 22 388
202 76
ERROR 388-185: Expecting an arithmetic operator.
ERROR 22-322: Syntax error, expecting one of the following: !, !!, &, *, **, +, ',', -, /, <, <=, <>, =, >, ><, >=, AND, EQ, GE,
GT, IN, LE, LT, MAX, MIN, NE, NG, NL, NOTIN, OR, ^=, |, ||, ~=.
ERROR 202-322: The option or parameter is not recognized and will be ignored.
ERROR 76-322: Syntax error, statement will be ignored.
142 ! proc import datafile= "&File." out= sheet1 dbms= xlsx replace;
____
22
142 ! range= "Sheet1$A:X"; getnames= yes; run; proc sort data= sheet1; by Type;
ERROR 22-322: Syntax error, expecting one of the following: !, !!, &, (, *, **, +, ',', -, /, <, <=, <>, =, >, ><, >=, AND, EQ, GE,
GT, IN, LE, LT, MAX, MIN, NE, NG, NL, NOTIN, OR, [, ^=, {, |, ||, ~=.
NOTE: The SAS System stopped processing this step because of errors.
NOTE: DATA statement used (Total process time):
real time 0.00 seconds
cpu time 0.00 seconds
ERROR: File WORK.SHEET1.DATA does not exist.
4 The SAS System 14:42 Sunday, January 3, 2021
NOTE: The SAS System stopped processing this step because of errors.
NOTE: PROCEDURE SORT used (Total process time):
real time 0.00 seconds
cpu time 0.00 seconds
ERROR: Physical file does not exist, C:\WINDOWS\system32\, strip(fname),.
NOTE: The SAS System stopped processing this step because of errors.
NOTE: PROCEDURE IMPORT used (Total process time):
real time 0.00 seconds
cpu time 0.00 seconds
ERROR: File WORK.SHEET2.DATA does not exist.
NOTE: The SAS System stopped processing this step because of errors.
NOTE: PROCEDURE SORT used (Total process time):
real time 0.00 seconds
cpu time 0.00 seconds
ERROR: File WORK.SHEET2.DATA does not exist.
And a further concern is: can I ask where I can write
put cmd = ;
to check to the syntax in case needed ?
Many thanks and warmest regards.
@Phil_NZ - This is how to check your command - it will just write the contents of cmd to your SAS log:
data _null_;
length fref $8 fname $200;
did = filename(fref,'C:\Users\pnguyen\Desktop\New folder');
did = dopen(fref);
do i = 1 to dnum(did);
fname = dread(did,i);
cmd=cats(%ImportAndTranspose(File=',
strip(fname), ', startsheet=1, endsheet=34);');
put cmd = ;
* call execute(cmd);
end;
did = dclose(did);
did = filename(fref);
keep fname;
run;
@Phil_NZ - Oops there's a quote missing:
data _null_;
length fref $8 fname $200;
did = filename(fref,'C:\Users\pnguyen\Desktop\New folder');
did = dopen(fref);
do i = 1 to dnum(did);
fname = dread(did,i);
cmd=cats('%ImportAndTranspose(File=',
strip(fname), ', startsheet=1, endsheet=34);');
put cmd = ;
* call execute(cmd);
end;
did = dclose(did);
did = filename(fref);
keep fname;
run;
Hi @SASKiwi , the log is as below, any abnormal things so far I should check ?
1 ;*';*";*/;quit;run;
2 OPTIONS PAGENO=MIN;
3 %LET _CLIENTTASKLABEL='replicate code for all sheets -included s34 _inc filenamer';
4 %LET _CLIENTPROCESSFLOWNAME='Process Flow';
5 %LET _CLIENTPROJECTPATH='C:\Users\pnguyen\OneDrive - Massey University\SAS\29_Dec_redo_all.egp';
6 %LET _CLIENTPROJECTPATHHOST='IT082760';
7 %LET _CLIENTPROJECTNAME='29_Dec_redo_all.egp';
8 %LET _SASPROGRAMFILE='';
9 %LET _SASPROGRAMFILEHOST='';
10
11 ODS _ALL_ CLOSE;
12 OPTIONS DEV=SVG;
13 GOPTIONS XPIXELS=0 YPIXELS=0;
14 %macro HTML5AccessibleGraphSupported;
15 %if %_SAS_VERCOMP_FV(9,4,4, 0,0,0) >= 0 %then ACCESSIBLE_GRAPH;
16 %mend;
17 FILENAME EGHTML TEMP;
18 ODS HTML5(ID=EGHTML) FILE=EGHTML
19 OPTIONS(BITMAP_MODE='INLINE')
20 %HTML5AccessibleGraphSupported
21 ENCODING='utf-8'
22 STYLE=HtmlBlue
23 NOGTITLE
24 NOGFOOTNOTE
25 GPATH=&sasworklocation
26 ;
NOTE: Writing HTML5(EGHTML) Body file: EGHTML
27
28 options compress=yes reuse=yes;
29
30 %macro ImportAndTranspose(
31 File=
32 , StartSheet=
33 , EndSheet=
34 );
35
36 %local i;
37
38 %do i = &StartSheet. %to &EndSheet.;
39
40 %if &i=1 %then %do;
41
42 proc import datafile= "&File."
43 out= sheet1
44 dbms= xlsx
45 replace;
46 range= "Sheet1$A:X";
47 getnames= yes;
48 run;
49
50 proc sort data= sheet1;
51 by Type;
52 run;
53 %end;
54
55 %else %if &i= &EndSheet. %then %do;
56 proc import datafile= "&File."
57 out= sheet&i.
2 The SAS System 14:42 Sunday, January 3, 2021
58 dbms= xlsx
59 replace;
60 range= "Sheet&i.$A:AG";
61 getnames= yes;
62 run;
63
64 proc sort data= sheet&i.;
65 by Type;
66 run;
67
68 proc transpose data= sheet&i.
69 out= sheet&i._out(rename=(COL1=s&i. _NAME_=Year) drop=_label_);
70 by Type;
71 VAR '1988'N - '2019'N;
72 run;
73 proc print data=sheet&i._out;
74 run;
75
76 data sheet&i._outx;
77 set sheet&i._out;
78 if s&i. in: ('NA', '$$') then s&i. =".";
79 run;
80
81 %end;
82
83
84 %else %if (&i ne 1) and (&i ne Endsheet.) %then %do;
85 proc import datafile= "&File."
86 out= sheet&i.
87 dbms= xlsx
88 replace;
89 range= "Sheet&i.$A:AG";
90 getnames= yes;
91 run;
92
93 proc sort data= sheet&i.;
94 by Type;
95 run;
96
97 proc transpose data= sheet&i.
98 out= sheet&i._out(rename=(COL1=s&i. _NAME_=Year) drop=_label_);
99 by Type;
100 VAR '1988'N - '2019'N;
101 run;
102 proc print data=sheet&i._out;
103 run;
104
105 DATA sheet&i._outx;
106 set sheet&i._out;
107
108 if s&i. not in: ('NA', '$$') then s&i.2=input(s&i., 32.);
109 drop s&i.;
110 run;
111 %end;
112
113
114
115 %end;
3 The SAS System 14:42 Sunday, January 3, 2021
116
117 %mend;
118
119 *Replicate all file in one folder;
120 data _null_;
121 length fref $8 fname $200;
122 did = filename(fref,'C:\Users\pnguyen\Desktop\New folder');
123 did = dopen(fref);
124 do i = 1 to dnum(did);
125 fname = dread(did,i);
126 cmd=cats('%ImportAndTranspose(File=',
127 strip(fname),',startsheet=1,endsheet=34);');
128 put cmd = ;
129 end;
130 did = dclose(did);
131 did = filename(fref);
132 keep fname;
133 run;
cmd=%ImportAndTranspose(File=Argentina_.xlsx,startsheet=1,endsheet=34);
cmd=%ImportAndTranspose(File=Bulgaria_.xlsx,startsheet=1,endsheet=34);
cmd=%ImportAndTranspose(File=Colombia_.xlsx,startsheet=1,endsheet=34);
NOTE: DATA statement used (Total process time):
real time 0.00 seconds
cpu time 0.00 seconds
134
135 %LET _CLIENTTASKLABEL=;
136 %LET _CLIENTPROCESSFLOWNAME=;
137 %LET _CLIENTPROJECTPATH=;
138 %LET _CLIENTPROJECTPATHHOST=;
139 %LET _CLIENTPROJECTNAME=;
140 %LET _SASPROGRAMFILE=;
141 %LET _SASPROGRAMFILEHOST=;
142
143 ;*';*";*/;quit;run;
144 ODS _ALL_ CLOSE;
145
146
147 QUIT; RUN;
148
Many thanks!
@Phil_NZ - Looks good to me. Try adding your CALL EXECUTE back in.
Thank you @SASKiwi , after putting the call execute back, it seems that the problem solved, but it seems that the program read the file not from the directory I order, leading to the error below:
As you can see, SAS read the data from C:\WINDOWS\system32\
while the directory is C:\Users\pnguyen\Desktop\New folder
options compress=yes reuse=yes;
44
45 %macro ImportAndTranspose(
46 File=
47 , StartSheet=
48 , EndSheet=
49 );
50
51 %local i;
52
53 %do i = &StartSheet. %to &EndSheet.;
54
55 %if &i=1 %then %do;
56
57 proc import datafile= "&File."
2 The SAS System 14:42 Sunday, January 3, 2021
58 out= sheet1
59 dbms= xlsx
60 replace;
61 range= "Sheet1$A:X";
62 getnames= yes;
63 run;
64
65 proc sort data= sheet1;
66 by Type;
67 run;
68 %end;
69
70 %else %if &i= &EndSheet. %then %do;
71 proc import datafile= "&File."
72 out= sheet&i.
73 dbms= xlsx
74 replace;
75 range= "Sheet&i.$A:AG";
76 getnames= yes;
77 run;
78
79 proc sort data= sheet&i.;
80 by Type;
81 run;
82
83 proc transpose data= sheet&i.
84 out= sheet&i._out(rename=(COL1=s&i. _NAME_=Year) drop=_label_);
85 by Type;
86 VAR '1988'N - '2019'N;
87 run;
88 proc print data=sheet&i._out;
89 run;
90
91 data sheet&i._outx;
92 set sheet&i._out;
93 if s&i. in: ('NA', '$$') then s&i. =".";
94 run;
95
96 %end;
97
98
99 %else %if (&i ne 1) and (&i ne Endsheet.) %then %do;
100 proc import datafile= "&File."
101 out= sheet&i.
102 dbms= xlsx
103 replace;
104 range= "Sheet&i.$A:AG";
105 getnames= yes;
106 run;
107
108 proc sort data= sheet&i.;
109 by Type;
110 run;
111
112 proc transpose data= sheet&i.
113 out= sheet&i._out(rename=(COL1=s&i. _NAME_=Year) drop=_label_);
114 by Type;
115 VAR '1988'N - '2019'N;
3 The SAS System 14:42 Sunday, January 3, 2021
116 run;
117 proc print data=sheet&i._out;
118 run;
119
120 DATA sheet&i._outx;
121 set sheet&i._out;
122
123 if s&i. not in: ('NA', '$$') then s&i.2=input(s&i., 32.);
124 drop s&i.;
125 run;
126 %end;
127
128
129
130 %end;
131
132 %mend;
133
134 *Replicate all file in one folder;
135 data _null_;
136 length fref $8 fname $200;
137 did = filename(fref,'C:\Users\pnguyen\Desktop\New folder');
138 did = dopen(fref);
139 do i = 1 to dnum(did);
140 fname = dread(did,i);
141 cmd=cats('%ImportAndTranspose(File=',
142 strip(fname),',startsheet=1,endsheet=34);');
143 put cmd = ;
144 call execute(cmd);
145 end;
146 did = dclose(did);
147 did = filename(fref);
148 keep fname;
149 run;
cmd=%ImportAndTranspose(File=Argentina_.xlsx,startsheet=1,endsheet=34);
cmd=%ImportAndTranspose(File=Bulgaria_.xlsx,startsheet=1,endsheet=34);
cmd=%ImportAndTranspose(File=Colombia_.xlsx,startsheet=1,endsheet=34);
NOTE: DATA statement used (Total process time):
real time 0.00 seconds
cpu time 0.00 seconds
NOTE: CALL EXECUTE generated line.
1 + proc import datafile= "Argentina_.xlsx" out= sheet1 dbms= xlsx
replace;
1 +
range= "Sheet1$A:X"; getnames= yes; run;
ERROR: Physical file does not exist, C:\WINDOWS\system32\Argentina_.
NOTE: The SAS System stopped processing this step because of errors.
NOTE: PROCEDURE IMPORT used (Total process time):
real time 0.00 seconds
cpu time 0.00 seconds
Can you please suggest to me how to sort it out?
Many thanks!
@Phil_NZ - Almost there. Need to add a path to your filename so SAS knows where to find your spreadsheet:
File=c:\MyFolder\Argentina_.xlsx
Hi @SASKiwi , thank you very much, it works well so far without any warnings or errors, however, the result is quite strange while it only show 100 output files as the picture while the actual number of the output file should be 34*3*3=306 results. One of the solutions I can think of is to delete some "not needed" output files, but I am wondering if there is any solution can be done without deleting these files?
Here is the full code so far
options compress=yes reuse=yes;
%macro ImportAndTranspose(
File=
, StartSheet=
, EndSheet=
);
%local i;
%do i = &StartSheet. %to &EndSheet.;
%if &i=1 %then %do;
proc import datafile= "&File."
out= sheet1
dbms= xlsx
replace;
range= "Sheet1$A:X";
getnames= yes;
run;
proc sort data= sheet1;
by Type;
run;
%end;
%else %if &i= &EndSheet. %then %do;
proc import datafile= "&File."
out= sheet&i.
dbms= xlsx
replace;
range= "Sheet&i.$A:AG";
getnames= yes;
run;
proc sort data= sheet&i.;
by Type;
run;
proc transpose data= sheet&i.
out= sheet&i._out(rename=(COL1=s&i. _NAME_=Year) drop=_label_);
by Type;
VAR '1988'N - '2019'N;
run;
proc print data=sheet&i._out;
run;
data sheet&i._outx;
set sheet&i._out;
if s&i. in: ('NA', '$$') then s&i. =".";
run;
%end;
%else %if (&i ne 1) and (&i ne Endsheet.) %then %do;
proc import datafile= "&File."
out= sheet&i.
dbms= xlsx
replace;
range= "Sheet&i.$A:AG";
getnames= yes;
run;
proc sort data= sheet&i.;
by Type;
run;
proc transpose data= sheet&i.
out= sheet&i._out(rename=(COL1=s&i. _NAME_=Year) drop=_label_);
by Type;
VAR '1988'N - '2019'N;
run;
proc print data=sheet&i._out;
run;
DATA sheet&i._outx;
set sheet&i._out;
if s&i. not in: ('NA', '$$') then s&i.2=input(s&i., 32.);
drop s&i.;
run;
%end;
%end;
%mend;
*Replicate all file in one folder;
data _null_;
length fref $8 fname $200;
did = filename(fref,'C:\Users\pnguyen\Desktop\New folder');
did = dopen(fref);
do i = 1 to dnum(did);
fname = dread(did,i);
cmd=cats('%ImportAndTranspose(File=C:\Users\pnguyen\Desktop\New folder\',
strip(fname),',startsheet=1,endsheet=34);');
put cmd = ;
call execute(cmd);
end;
did = dclose(did);
did = filename(fref);
keep fname;
run;
And a further question: because the sheet2 results from Argentina or Colombia all sheet2_outx, which may confuse me later on, I am wondering is there any chance to add something in my code to have the results like: sheet2_Arg_outx and sheet2_Col_outx.
@Phil_NZ - I suggest you use say the first three characters of your filename and add that as a prefix to your output dataset names like Arg_Sheet1_Outx. Easy enough to do by using SUBSTR on your FNAME variable, then passing it through to your macro as an extra macro parameter. I'll leave it up to you to try.
Hi @SASKiwi . Thank you for your suggestion, I gave it a try but it does not work so far. Generally speaking, I use CATS to concatenate the string together, but it does not work, can you please give me a hint or else?
Many thanks and warmest regards!
options compress=yes reuse=yes;
%macro ImportAndTranspose(
File=
, StartSheet=
, EndSheet=
);
%local i;
%do i = &StartSheet. %to &EndSheet.;
%if &i=1 %then %do;
proc import datafile= "&File."
out= cats(substr(fname,1,3),sheet1)
dbms= xlsx
replace;
range= "Sheet1$A:X";
getnames= yes;
run;
proc sort data= cats(substr(fname,1,3),sheet1);
by Type;
run;
%end;
%else %if &i= &EndSheet. %then %do;
proc import datafile= "&File."
out= cats(substr(fname,1,3),sheet&i.)
dbms= xlsx
replace;
range= "Sheet&i.$A:AG";
getnames= yes;
run;
proc sort data= cats(substr(fname,1,3),sheet&i.);
by Type;
run;
proc transpose data= cats(substr(fname,1,3,sheet&i.)
out= cats(substr(fname,1,3),sheet&i._out)(rename=(COL1=s&i. _NAME_=Year) drop=_label_);
by Type;
VAR '1988'N - '2019'N;
run;
proc print data= cats(substr(fname,1,3),sheet&i._out);
run;
data cats(substr(fname,1,3),sheet&i._outx);
set cats(substr(fname,1,3),sheet&i._out);
if s&i. in: ('NA', '$$') then s&i. =".";
run;
%end;
%else %if (&i ne 1) and (&i ne Endsheet.) %then %do;
proc import datafile= "&File."
out= cats(substr(fname,1,3),sheet&i.)
dbms= xlsx
replace;
range= "Sheet&i.$A:AG";
getnames= yes;
run;
proc sort data= cats(substr(fname,1,3),sheet&i.);
by Type;
run;
proc transpose data= cats(substr(fname,1,3),sheet&i.)
out= cats(substr(fname,1,3),sheet&i._out)(rename=(COL1=s&i. _NAME_=Year) drop=_label_);
by Type;
VAR '1988'N - '2019'N;
run;
proc print data=cats(substr(fname,1,3),sheet&i._out);
run;
data cats(substr(fname,1,3),sheet&i._outx);
set cats(substr(fname,1,3),sheet&i._out);
if s&i. not in: ('NA', '$$') then s&i.2=input(s&i., 32.);
drop s&i.;
run;
%end;
%end;
%mend;
*Replicate all file in one folder;
data _null_;
length fref $8 fname $200;
did = filename(fref,'C:\Users\pnguyen\Desktop\New folder');
did = dopen(fref);
do i = 1 to dnum(did);
fname = dread(did,i);
cmd=cats('%ImportAndTranspose(File=C:\Users\pnguyen\Desktop\New folder\',
strip(fname),',startsheet=1,endsheet=34);');
put cmd = ;
call execute(cmd);
end;
did = dclose(did);
did = filename(fref);
keep fname;
run;
The log is like that
1 + proc import datafile= "C:\Users\pnguyen\Desktop\New folder\Argentina_.xlsx" out=
1 !+cats(substr(fname,1,3),sheet1) dbms= xlsx replace; range= "Sheet1$A:X";
______
22
ERROR 22-7: Invalid option name SUBSTR.
1 !+cats(substr(fname,1,3),sheet1) dbms= xlsx replace; range= "Sheet1$A:X";
_
22
1 !+ getnames= yes; run;
4 The SAS System 09:25 Monday, January 4, 2021
ERROR 22-7: Invalid option name ,.
BEFORE you start to make code dynamic, that code has to work without any macro coding.
This
proc print data= cats(substr(fname,1,3),sheet&i._out);
run;
will NEVER work, as you cannot use functions or dataset variables in procedure options.
If you want to build a dataset name from macro variables, you have to use those, and use macro functions:
data=%substr(&fname,1,3)sheet&i._out
Suppose that &fname contains XXXYYY, and &i 1, this would result in
XXXsheet1_out
@Phil_NZ , pay attention that FNAME is available only in the step:
*Replicate all file in one folder;
data _null_;
length fref $8 fname $200;
did = filename(fref,'C:\Users\pnguyen\Desktop\New folder');
did = dopen(fref);
do i = 1 to dnum(did);
fname = dread(did,i);
cmd=cats('%ImportAndTranspose(File=C:\Users\pnguyen\Desktop\New folder\',
strip(fname),',startsheet=1,endsheet=34);');
put cmd = ;
call execute(cmd);
end;
did = dclose(did);
did = filename(fref);
keep fname;
run;
and is not available at macro execution, there fore you need to supply it as a separate argument to the macro.
Step-1) adapt he macro to receive a new argument:
options compress=yes reuse=yes;
%macro ImportAndTranspose(
File=
,outf= /* new argument */
, StartSheet=
, EndSheet=
);
.......
/* adapt each proc import to : */
proc import datafile= "&File."
out= &outf.1 /* or &outf.&i */
dbms= xlsx
replace;
.........
Step-2) Supply the new argument to the macro:
*Replicate all file in one folder;
data _null_;
length fref $8 fname $200 short_fn $3;
did = filename(fref,'C:\Users\pnguyen\Desktop\New folder');
did = dopen(fref);
do i = 1 to dnum(did);
fname = dread(did,i);
short_fn = substr(fname,1,3);
cmd=cats('%ImportAndTranspose(File=C:\Users\pnguyen\Desktop\New folder\',
strip(fname),',outf=',short_fn,'sheet,startsheet=1,endsheet=34);');
put cmd = ;
call execute(cmd);
end;
did = dclose(did);
did = filename(fref);
keep fname;
run;
Thank you very much @Shmuel and @SASKiwi , your helps are just amazing.
Now the code works very well.
Can I ask some questions of curiosity?
* 1. @Shmuel , it seems that your code has one redundant part "sheet" right?
cmd=cats('%ImportAndTranspose(File=C:\Users\pnguyen\Desktop\New folder\',
strip(fname),',outf=',short_fn,'sheet,startsheet=1,endsheet=34);');
I deleted the word "sheet" and it works.
2. I see the way @SASKiwi use the command "put" to check if there is anything wrong in the code running quite impressive and can be widely applied in the future, so I am not sure if you can summarize how should we use it properly or any link that briefly explains this code?
*And regarding my code in replicating all file in one folder, I have two questions:
data _null_;
length fref $8 fname $200;
did = filename(fref,'C:\Users\pnguyen\Desktop\New folder');
did = dopen(fref);
do i = 1 to dnum(did);
fname = dread(did,i);
short_fn= cats(substr(fname, 1,3),'_');
cmd=cats('%ImportAndTranspose(File=C:\Users\pnguyen\Desktop\New folder\',
strip(fname),',outf=',short_fn,',startsheet=1,endsheet=34);');
put cmd = ;
call execute(cmd);
end;
did = dclose(did);
did = filename(fref);
keep fname;
run;
3. Why this code does not work
cmd=cats('%ImportAndTranspose(File=',
strip(fname),',outf=',short_fn,',startsheet=1,endsheet=34);');
that I need to enter the directory path to make it up and running?
cmd=cats('%ImportAndTranspose(File=C:\Users\pnguyen\Desktop\New folder\',
strip(fname),',outf=',short_fn,',startsheet=1,endsheet=34);');
I ask this question because I already call the directory upfront, so I am wondering that "C:\Users\pnguyen\Desktop\New folder\"
is a kind of redundant in cats function, but without it, the code run wrongly
4. What is the difference between the variable fref and fname in the code above. I understand that fname is about the name of the file in this folder (says: Argentina_) and length of fname is limited by 200 characters, but what is fref actually, why its length is 8 characters?
It's finally time to hack! Remember to visit the SAS Hacker's Hub regularly for news and updates.
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.
Ready to level-up your skills? Choose your own adventure.