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

Hi Reader,

 

My requirement is &output_date . I have created below program but no satisfied and still I want to cut short this macro.

 

Kindly suggest me more dynamic way for below mention senerio to get &output_date. Or there any other approch which I can do it.

 

data un_date ;
input date1$ 10.;
CARDS;
2001-UN-UN
2002-12-UN
2006-11-UN
2004-UN-02
2001
;
run;

 

****My pr0gram*****

 

%macro offset_date(date1, output_date, indset , outdset);
data &outdset ;
set &indset ;
if &date1 ne "" then do ;
if index(&date1,"UN")=0 then &output_date=&date1;
else if index(&date1,"UN")> 0 then do;
if scan(&date1,2,"-") eq "UN" and scan(&date1,3,"-") ne "UN" then &output_date=tranwrd(&date1,"-UN-","----");
if scan(&date1,2,"-") ne "UN" and scan(&date1,3,"-") eq "UN" then &output_date=tranwrd(&date1,"-UN","");
if scan(&date1,2,"-") eq "UN" and scan(&date1,3,"-") eq "UN" then &output_date=tranwrd(&date1,"-UN-UN","");
end;
end;
run;
%mend offset_date;
%offset_date(date1, output_date, un_date, un_data);

1 ACCEPTED SOLUTION

Accepted Solutions
ChrisNZ
Tourmaline | Level 20

Another way

data WANT ;
  input DATE1 $10.; 
  DATE2 = prxchange( 's/-UN//', 2, prxchange( 's/(\d-)UN(-\d)/\1--\2/', 1, DATE1 ) );
cards;
2001-UN-UN
2002-12-UN
2006-11-UN
2004-UN-02
2001
run;
Obs DATE1 DATE2
1 2001-UN-UN 2001
2 2002-12-UN 2002-12
3 2006-11-UN 2006-11
4 2004-UN-02 2004----02
5 2001 2001

 

 

View solution in original post

8 REPLIES 8
mkeintz
PROC Star

You're telling us that your code is not satisfactory, yet you don't tell us what you want the results to look like.  Please provide the desired values for each of your starting values. 

 

Below is just a guess on my part.  But you would probably get more, and better, responses is you showed explicit desired results.  Help us help you.

 

data un_date ;
input &date1$ 10.;
CARDS;
2001-UN-UN
2002-12-UN
2006-11-UN
2004-UN-02
2001
;
run;
%let date1=date1;
%let output_date=date2;
data want;
  set un_date;
  &output_date=&date1 ;
  if index(&date1,'UN')>0 then do;
    &output_date=tranwrd(&output_date,'-UN-UN','');    
    &output_date=tranwrd(&output_date,'-UN-','----'); 
    &output_date=tranwrd(&output_date,'-UN','');      
  end;
run;

You can put this code into a macro, instead my open code solution.

 

I think you should bother with scanning for specific pattern combinations.  Instead transform in this specific sequence: the double UN first, then the trailing UN, and the internal UN.  There will be no need for if tests since whichever of these conditions is discovered first, subsequent conditions will not arise.

--------------------------
The hash OUTPUT method will overwrite a SAS data set, but not append. That can be costly. Consider voting for Add a HASH object method which would append a hash object to an existing SAS data set

Would enabling PROC SORT to simultaneously output multiple datasets be useful? Then vote for
Allow PROC SORT to output multiple datasets

--------------------------
pdhokriya
Pyrite | Level 9
Thank you so much for the suggested solution.

Can you share the syntax in Proc sql too.
mkeintz
PROC Star

@pdhokriya wrote:
Thank you so much for the suggested solution.

Can you share the syntax in Proc sql too.

I leave that to you.  But here's a data step program that you should be able to replicate in SQL using the CASE expression:

 

data want;
  set un_date;
  if index(&date1,'-UN-UN') then &output_date=tranwrd(&date1,'-UN-UN','');    else
  if index(&date1,'-UN-')   then &output_date=tranwrd(&date1,'-UN-','----');  else
  &output_date=tranwrd(&date1,'-UN','');      
run;
--------------------------
The hash OUTPUT method will overwrite a SAS data set, but not append. That can be costly. Consider voting for Add a HASH object method which would append a hash object to an existing SAS data set

Would enabling PROC SORT to simultaneously output multiple datasets be useful? Then vote for
Allow PROC SORT to output multiple datasets

--------------------------
pdhokriya
Pyrite | Level 9
So more than 1 date how can I handle ?
data WANT ;
input cmstdat $10. cmendat $11.;
cards;
2001-UN-UN 2001-UN-01
2002-12-UN 2001
2006-11-UN 2001-01-UN
2004-UN-02 2001-UN-02
2008-03-03
2001

;
run;

%let input_date=cmstdat;
%let output_date=cmstdtc;

data example3;
set want;
&output_date=&input_date ;
if index(&input_date,'UN')>0 then do;
&output_date=tranwrd(&output_date,'-UN-UN','');
&output_date=tranwrd(&output_date,'-UN-','----');
&output_date=tranwrd(&output_date,'-UN','');
end;
run;


So Can I use %macro; %mend?
ChrisNZ
Tourmaline | Level 20

Another way

data WANT ;
  input DATE1 $10.; 
  DATE2 = prxchange( 's/-UN//', 2, prxchange( 's/(\d-)UN(-\d)/\1--\2/', 1, DATE1 ) );
cards;
2001-UN-UN
2002-12-UN
2006-11-UN
2004-UN-02
2001
run;
Obs DATE1 DATE2
1 2001-UN-UN 2001
2 2002-12-UN 2002-12
3 2006-11-UN 2006-11
4 2004-UN-02 2004----02
5 2001 2001

 

 

Tom
Super User Tom
Super User

I am curious.  What is the meaning of a value like  2004-UN-02?  Is that supposed to indicate that it was the second day of the month but they can't remember which month?  How much values does the 02 actually add in that case?

pdhokriya
Pyrite | Level 9
I am not sure about your question but still for your understanding , ----------------------------yyyy-mm-dd format so if month is missing we generally cosider it UN in raw data , targeted data we consider it as "--" so in future it can be 01 to 12 month.

Hope you get it.
Tom
Super User Tom
Super User

I get the idea of translating UN to hyphens.

My question why would you keep the day of the month when the actual month is not present.  How can you have any confidence in the day of the month provided if the month itself is not known?  Perhaps it is even more likely that they meant the month number and not the day number.

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
  • 8 replies
  • 1329 views
  • 4 likes
  • 4 in conversation