BookmarkSubscribeRSS Feed
sandrube
Fluorite | Level 6

Wish everyone a Happy and Prosperous New Year!!!

 

I and trying to transpose the following data based on date.

 

data have;
input ID $ Vit_D CRP date :mmddyy10.;
format date mmddyy10.;
cards;
00-01 12 5.5 09/05/2021
00-01 15 1.6 10/12/2021
00-03 18 3.9 10/17/2021
00-03 26 3.8 09/16/2021
00-05 36 1.5 09/01/2021
00-05 30 0.8 10/20/2021
00-06 43 10.3 09/24/2021
00-06 52 0.8 10/25/2021
;

 

The outcome I am trying to get is following.

 

data have_1;
input ID $ Vit_D_1 CRP_1 date_1 :mmddyy10. Vit_D_2 CRP_2 date_2 :mmddyy10.;
format date_1 mmddyy10. date_2 mmddyy10.;
cards;
00-01 12 5.5 09/05/2021 15 1.6 10/12/2021
00-03 18 3.9 10/17/2021 26 3.8 09/16/2021
00-05 36 1.5 09/01/2021 30 0.8 10/20/2021
00-06 43 10.3 09/24/2021 52 0.8 10/25/2021
;

 

I am struggling because I am trying to do it based on dates. Could anyone help.

 

Thanks you very much!

Rube

 

3 REPLIES 3
andreas_lds
Jade | Level 19

The structure of HAVE is almost always the preferred one, because it is easier to use in most procedures: you have to write less code. So the question arises: why do you need a wide dataset?

 

If you insist on transposing: You have to call proc transpose for each variable you want transposed.

Example:

proc transpose data=have out=t_date(drop=_name_) prefix=date_;
   by id;
   var date;
run;

And finally you have to merge all the created datasets.

 

If your dataset is large, the following step might perform better:


%macro transpose;
   %local maxCount;
   
   proc sql noprint;
      select max(count) into :maxCount trimmed
         from (
         select count(Id) as count
            from work.have 
               group by id
         );
   quit;


   data want;
      set have;
      by Id;
      
      length
         %do i = 1 %to &maxCount.;
            vit_d_&i. crp_&i. date_&i. 8
         %end;
      ;
      
      format date_: mmddyy10.;
      
      retain i vit_d_: crp_: date_:;
      
      array vits[&maxCount.] vit_d_1 - vit_d_&maxCount.;
      array crps[&maxCount.] crp_1 - crp_&maxCount.;
      array dates[&maxCount.] date_1 - date_&maxCount.;      
      
      if first.Id then do;
         call missing(of vit_d_:, of crp_:, of date_:);
         i = 1;
      end;
      
      vits[i] = vit_d;
      crps[i] = crp;
      dates[i] = date;
      
      i = i + 1;
      
      if last.Id then do;
         output;
      end;
      
      drop i crp vit_d date;
   run;
%mend;


%transpose;
Ksharp
Super User
data have;
input ID $ Vit_D CRP date :mmddyy10.;
format date mmddyy10.;
cards;
00-01 12 5.5 09/05/2021
00-01 15 1.6 10/12/2021
00-03 18 3.9 10/17/2021
00-03 26 3.8 09/16/2021
00-05 36 1.5 09/01/2021
00-05 30 0.8 10/20/2021
00-06 43 10.3 09/24/2021
00-06 52 0.8 10/25/2021
;

data temp;
set have;
by id;
if first.id then n=0;
n+1;
run;
proc sql noprint;
select distinct catt('temp(where=(n=',n,') rename=(Vit_D=Vit_D_',n,' CRP=CRP_',n,' date=date_',n,'))')
 into : merge separated by ' '
  from temp;
quit;
data want;
 merge &merge;
 by id;
 drop n;
run;
AndreaVianello
Obsidian | Level 7
very elegant program !

SAS Innovate 2025: Register Now

Registration is now open for SAS Innovate 2025 , our biggest and most exciting global event of the year! Join us in Orlando, FL, May 6-9.
Sign up by Dec. 31 to get the 2024 rate of just $495.
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.

SAS Training: Just a Click Away

 Ready to level-up your skills? Choose your own adventure.

Browse our catalog!

Discussion stats
  • 3 replies
  • 597 views
  • 3 likes
  • 4 in conversation