BookmarkSubscribeRSS Feed
JonesSmith
Calcite | Level 5

Hi, expert

Most of the time when I come to CALL SMPUT() in daily programming work, I always get unexpected macro errors.  Please help to correct me.

I always need to set a macro to store the exact days of certain month in financial report and retrieve them in data steps.  But the newly created variables yy, mm and dd  are all in 20178 (ie 2015-3-31), not 2015-3-1, 2015-3-2....... and 2015-3-31 as I expect.

e.g.

%macro report;
  data report;
    do loop=mdy(3,1,2015) to mdy(3,31,2015);
       call symput("x",loop);     /* where &x in dates need to be referred in later part */;

       xx=&x;

       cyear=year(&x);
       cmonth=month(&x);
       cdate=day(&x);

       output;
    end;
  run;
%mend report;

%report;

regards

jones

7 REPLIES 7
Reeza
Super User

This is the correct behaviour. SAS stored dates as numbers, where 1 is Jan 1, 1960 and 2 is Jan 2, 1960 and so forth.

If you want a specified display format you need to apply a format. Note that it will have leading zeros, ie 04 and 01 in month/day values Smiley Happy

For a year month day format, such as 2014-04-01 use

call symput("x",put(loop, yymmddd10.); 

Cynthia_sas
SAS Super FREQ

Hi:

  In SAS dates, 0 is January 1, 1960 and 1 is January 2, 1960 and -1 is Dec 31, 1959. You can run this program to see that 0 is Jan 1, 1960.

Cynthia

data whatdate;

  infile datalines;

  input thedate;

  put "Internal value " thedate= 'Now formatted: ' thedate= mmddyy10.;

return;

datalines;

0

1

2

-1

-2

-3334

18439

19912

;

run;

Reeza
Super User

Thanks for the correction!

JonesSmith
Calcite | Level 5

Thanks for your help.

regards

jones

Ksharp
Super User

Maybe that error be generated by blank in macro variable. Try call symputX() .

RW9
Diamond | Level 26 RW9
Diamond | Level 26

Hi,

I am not sure on the point of your macro.  You are going to hit problems as you are generating a macro variable with a datastep loop.  So the macro pre-processor gets your code, it does a search and replace on the &x. and finds nothing delclared for X so it throws an error, it never gets to the stage where the datastep is actually run to create X.

In your example X always referencing the last mdy, this is because the loop goes over each time and only the last iteration sets the date.

So first question, what is it your trying to achieve?  Is it to find all dates within that range and use them to select data, if so then store to dataset and use this in your code, e.g.:

data dates;

     attrib mydate format=date9.;

    do loop=mdy(3,1,2015) to mdy(3,31,2015);

          mydate=loop;

          output;
    end;
run;

/*later on */

proc sql;

     create table DATA_TO_WORK_ON as    

     select     *

     from       DATA_I_HAVE

     where     DATE in (select MYDATE from WORK.DATES);

quit;

JonesSmith
Calcite | Level 5

That's great !  Thank you all of you.

sas-innovate-2024.png

Join us for SAS Innovate April 16-19 at the Aria in Las Vegas. Bring the team and save big with our group pricing for a limited time only.

Pre-conference courses and tutorials are filling up fast and are always a sellout. Register today to reserve your seat.

 

Register now!

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.

Click image to register for webinarClick image to register for webinar

Classroom Training Available!

Select SAS Training centers are offering in-person courses. View upcoming courses for:

View all other training opportunities.

Discussion stats
  • 7 replies
  • 1841 views
  • 1 like
  • 5 in conversation