DATA Step, Macro, Functions and more

Do While Loop

Reply
Regular Contributor
Posts: 229

Do While Loop

[pre]
options symbolgen;
%let groupvalues="Lot_Id,Facility";
%let nrGroupValues = %sysfunc(countw(&groupvalues,' '));
%put &nrGroupValues;


%macro test;
%if "&groupvalues" ne ' ' %then %do;
nrGroupValues = %sysfunc(countw(&groupvalues,','));
%do %while(CounterVariable le nrGroupValues);
GroupValue = scan(&groupvalues,CounterVariable,' ');
%put &nrGroupValues;
%put CounterVariable;
%put GroupValue;


CounterVariable = CounterVariable + 1;
%end;
%end;
%mend;
%test;

[/pre]
what is wrong with this code?
it crashes on multiple places Message was edited by: Filipvdr
Regular Contributor
Posts: 171

Re: Do While Loop

It seems that you are mixing up data step statements and macro statements in multiple places. Is this what you were trying do?

[pre]
let groupvalues=Lot_Id,Facility; /* Removed quotation marks. These would cause problems when ***/
/* you reference the macro variable as "&GroupValues" later. ***/

%let nrGroupValues = %sysfunc(countw(&groupvalues,)); /*** The second argument to the countw function ***/
/*** was set to missing. The single quote was ***/
/*** treated as a delimiter in the previous code ***/
%put &nrGroupValues;

%macro test;

%local CounterVariable GroupValue; /*** Initialize variables that are local to this macro ***/
%if &groupvalues ne %then %do; /*** Removed unneeded quotation marks in this statement. ***/

/*nrGroupValues = %sysfunc(countw(&groupvalues,','));*/ /*** Removed redundant assignment statement. The ***/
/*** macro variable nrGroupValues has already ***/
/*** been created. This form of assignment statement ***/
/*** is only valid inside a data step. ***/

%let CounterVariable=1; /*** Initialized macro variable CounterVariable. ***/
%do %while (%eval(&CounterVariable le &nrGroupValues)); /*** CounterVariable and nrGroupValues are macro ***/
/*** variables and are therefore referenced with the ***/
/*** preceding &. ***/

%let GroupValue = %qscan(%bquote(&groupvalues), &CounterVariable); /*** %let is used to create a macro variable. ***/
/*** The macro function %qscan should be used ***/
/*** instead of the datastep scan function. The ***/
/*** %bquote function performs macro quoting so that ***/
/*** the comma present in the GroupValues value is ***/
/*** not interpreted as a delimiter to %qscan ***/
/*** function. CounterVariable is a macro variable ***/
/*** and is therefore referenced with the preceding & ***/
%put nrGroupValues = &nrGroupValues;
%put CounterVariable = &CounterVariable;
%put GroupValue = &GroupValue;

%let CounterVariable = %eval(&CounterVariable + 1); /*** The %eval function is used to increment the macro variable ***/
/*** CounterVariable. ***/
%end;
%end;
%mend;
%test;
[/pre]
Contributor
Posts: 24

Re: Do While Loop

> [pre]
> options symbolgen;
> %let groupvalues="Lot_Id,Facility";
> %let nrGroupValues = %sysfunc(countw(&groupvalues,'
> '));
> %put &nrGroupValues;
>
>
> %macro test;
> %if "&groupvalues" ne ' ' %then %do;
> nrGroupValues = %sysfunc(countw(&groupvalues,','));
> %do %while(CounterVariable le nrGroupValues);
> GroupValue = scan(&groupvalues,CounterVariable,'
> ' ');
> %put &nrGroupValues;
> t CounterVariable;
> %put GroupValue;
> CounterVariable = CounterVariable + 1;
> %end;
> %end;
> %mend;
> %test;
>
> [/pre]
> what is wrong with this code?
> it crashes on multiple places
>
> Message was edited by: Filipvdr

I think the problem is that with the Variable CounterVariable, nrGroupValues and GroupValue. The variables are being referenced without '&' and are being initialized without %let.

It looks like you are using Datastep Variables and Functions (SCAN) within the macro that does not have a datastep at all.

Try this:
options nosymbolgen;
%let groupvalues="Lot_Id,Facility";
%let nrGroupValues = %sysfunc(countw(&groupvalues,' '));
%put nrGroupValues_1: &nrGroupValues;

%let CounterVariable=1;

%macro test;
%if &groupvalues ne ' ' %then %do;
%let nrGroupValues = %sysfunc(countw(&groupvalues,','));
%do %while(&CounterVariable le &nrGroupValues);
%let GroupValue = %scan(&groupvalues,&CounterVariable,' ');
%put nrGroupValues_2 : &nrGroupValues;
%put CounterVariable: &CounterVariable;
%put GroupValue: &GroupValue;
%let CounterVariable = %eval(&CounterVariable + 1);
%end;
%end;
%mend;

%test;


Log:
nrGroupValues_1: 1

nrGroupValues_2 : 2
CounterVariable: 1
GroupValue: "Lot_Id,Facility"
nrGroupValues_2 : 2
CounterVariable: 2
GroupValue:

This runs without any error. But I did not understand what you are trying to achieve.


Message was edited by: bhavani

Message was edited by: bhavani Message was edited by: bhavani
Ask a Question
Discussion stats
  • 2 replies
  • 127 views
  • 0 likes
  • 3 in conversation