BookmarkSubscribeRSS Feed
mathberd
Calcite | Level 5

The following is a piece of my program. I would like to count how many times a particular number has borrowed for the last 30 days.

 

 

%MACRO LOOP(dataset);

%DO I=1 %TO 10; 
proc sql outobs=1;
select count(*) from &dataset
where msisdn = &&msisdn&I and 
abs(datepart(advance_datetime) - 
datepart((select advance_datetime from &dataset where msisdn = &&msisdn&I
order by advance_datetime desc limit 1)) < 31;
quit;
%END;
%MEND LOOP;
%LOOP(credit.bbhistory);

When I run it, it generated the following error message(see the bellow snapshot).

Please, help me and tell me what I am doing wrong.

Order by error.JPG

10 REPLIES 10
RW9
Diamond | Level 26 RW9
Diamond | Level 26

Could be a few things, but first off order by does not work in sub queries.  Also, at no point in that code is: MSISDN declared.  

 

The question is why do it this way in the first place?  There is no explanation for the whole do loop for instance.  However if I wanted to get a count based on a condition then the steps are simple:

1) create a category to indicate if the value is within a window

2) count based on the category

 

For example:

data want;
  set have;
  if date between low and high then cat="Y";
run;

proc sql;
  create table WANT as
  select  count(*) as RESULT
  from    WANT
  group by CAT;
quit;

That would give you a two way result, count of those having Y and those not.  Also, follow the guidance 

mathberd
Calcite | Level 5
@RW9, thanks for your input. This is for clarification.
As you can see the msisdn is a macro variable, it has been declared outside of the loop function. additionally, the reason I wished to get the counts in that way, is to avoid creating intermediary datasets
RW9
Diamond | Level 26 RW9
Diamond | Level 26

Please ensure you post all relelvant information in the post.  As for not wanting to creating an intermediate dataset - you are creating an intermediate dataset (for each iteration of the do loop) however you just don't see it.  The method you are using here will not be more efficient than having one dataset and one count procedure, as yours will always be * 10.

mathberd
Calcite | Level 5
@RW9, Ok. Let me then try your steps
Kurt_Bremser
Super User

Run the SQL outside of a macro and macro loop (set the macro variable i manually), and look at the log. The ERROR message will point to the location of the error, and make it easier to debug.

mathberd
Calcite | Level 5
%MACRO LOOP(dataset);
 
%DO I=1 %TO 10; 
proc sql outobs=1;

select count(*) from &dataset
where msisdn = &&msisdn&I and 
abs(datepart(advance_datetime) - 
datepart((select advance_datetime from &dataset 
where msisdn = &&msisdn&I order by advance_datetime desc limit 1))) < 31;
quit;

%END;
%MEND LOOP; 

%LOOP(credit.bbhistory);

This is the codes after adding the fourth closing. Like you mentioned, it was the problem. However, it did not get completely resolved.

This is what I got ; error message due to limit statement

limit error.JPG

mathberd
Calcite | Level 5
this is part of my code (it's a function which can be called anytime )
Kurt_Bremser
Super User

Please supply link to the documentation for "limit". 😉

 

There is no limit statement or function in SAS.

If you want to limit the number of output observations from proc sql, look into the outobs= option for the proc sql statement.

 

limit n works in MySQL, but it is not standard SQL language.

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
  • 10 replies
  • 2386 views
  • 0 likes
  • 3 in conversation