BookmarkSubscribeRSS Feed
mcook
Quartz | Level 8

Given a table such as: 

 

data TempMax;
    input ID A B C D E;
    datalines;
        1 234 432 245 555 546
        2 334 258 593 599 113
        3 948 874 737 333 388
        ;
    run;


Obs ID A B C D E 1 1 234 432 245 555 546 2 2 334 258 593 599 113 3 3 948 874 737 333 388

 

 

and performing a max function on it

 

 data TempMax;
        set TempMax;
            latestdate = max(A,B,C,D,E);
        run;

to give

Obs    ID     A      B      C      D      E     latestdate

 1      1    234    432    245    555    546        555   
 2      2    334    258    593    599    113        599   
 3      3    948    874    737    333    388        948   

 

Is there a way to determine which variable was the max?  either by identifying the variable, or its argument position in the max function? 

Also, the values in the dataset I am working with are dates. and no 2 dates in an obs are equal.  so there is one and only one argument to the max function that will be the max. 

 

 

 

 

3 REPLIES 3
Rick_SAS
SAS Super FREQ

Yes. I think is easiest if you put the variables into an array and use the OF keyword to supply the values to the MAX function, like this:  MAX(of arrayName[*}) .

 

Anyway, the function you want is the WHICHN function, which returns the (first) index of a list a variables that equals a specified value.

So first compute the max, then use WHICHN to find out which variables (1st, 2nd, 3rd, etc) it matches. If necessary, you can use the VNAME function to get the name of the variable:

 

/* use OP's data */
data TempMax;
set TempMax;
array myVars[*] A B C D E;  /* or A--E if contiguous */
length varName $32;
date1 = max(A,B,C,D,E);       /* OP's current code */
maxDate = max(of myVars[*]);  /* an equivalent computation that uses arrays */
/* WHICHN function: https://go.documentation.sas.com/doc/en/pgmsascdc/9.4_3.5/lefunctionsref/p0zs0pv38mel2jn1in4lte2akx4d.htm */
Index = whichn(maxDate, of myVars[*]);
/* VARNAME function: https://go.documentation.sas.com/doc/en/pgmsascdc/9.4_3.5/lefunctionsref/n1cjm0xdeczcd5n1s7d8ah9x8432.htm */
varName = vname(myVars[Index]);
run;


proc print data=TempMax; 
   var ID A B C D E maxDate Index varName;
run;
ballardw
Super User

I am a bit confused as to why you are calling your maximum value "latestdate". If your values are actually dates then use dates for your example. When you show values like 234 it makes one suspect that you may not have actual SAS date values and will have other problems later.

 

data TempMax;
    input ID  A :date9. B :date9. C :date9. D :date9. E :date9. ;
    format a b c d e date9.;
datalines;
1 01JAN2019 03FEB2019 04AUG2020 11NOV2021 12DEC2022
2 15DEC2022 10OCT2022 08AUG2021 06JUN2018 04APR2019
3 11OCT2023 08MAR2018 09FEB2022 22JAN2021 30MAR2017
;
  
FreelanceReinh
Jade | Level 19

Alternatively, start with a "long" dataset or create one from your existing data:

proc transpose data=TempMax out=long;
by id;
run;

Then you can use PROC SUMMARY (or PROC SQL) to obtain the desired output quite naturally:

proc summary data=long;
by id;
var col1;
id _name_;
output out=want(drop=_:) max=maxdate maxid=varname;
run;

Ready to join fellow brilliant minds for the SAS Hackathon?

Build your skills. Make connections. Enjoy creative freedom. Maybe change the world. Registration is now open through August 30th. Visit the SAS Hackathon homepage.

Register today!
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
  • 3 replies
  • 394 views
  • 4 likes
  • 4 in conversation