Hello,
Is it possible to create a variable from the value of another variable?
Like this:
data aaaaa;
infile datalines delimiter='09'x;
length uuu$2 vvv$2;
input uuu $ vvv $;
datalines;
aa gg
bb hh
cc ii
dd jj
ee kk
ff ll
;
data bbbbb;
set aaaaa;
*create a variable from the value of uuu;
<<value_of_uuu>> = 'something';
/* (and this single line would produce something like this:
aa='something' when _N_=1;
bb='something' when _N_=2;
cc='something' when _N_=3;
etc. )*/
run;
I don't know if this is possible.
This may seem unusefull, it is the simplification of my problem which has several do-loops inside the datastep.
Let me know if I need to explain more, but I feel it would quickly overcomplicate the question.
Thanks!
--
SAS9.3, EG7.1, Windows7
I agree with @ballardw, the request is quite odd. You can do it, quite easily, but I don't understand why you want to:
data _null_; set aaaa end=last; if _n_=1 then call execute('data want; set aaaa; '); call execute(cat(' ',strip(uu),'="',strip(vv),'";'); if last then call execute(';run;'); run;
This assumes all character. Why though is the real question.
Edit, for @Astounding, you could modify mine above to handle numbers/characters, and check existence and such like - its one of the benefits of generated code over arrays.
Errm, you have read the SAS guide yes, and understand base SAS? Its just you have more or less written the code but seem to question a fundemental. Use conditional branching, either if then's or select;
data want; set have; if _n_=1 then aa=""; if _n_=2 then bb=""; ... run;
That's not it, maybe I wasn't clear, I will edit the question. I know base SAS.
Here I don't want to write aa = '' I want to write something like
value_of_uuu = ''
and that value_of_uuu would be replace by aa in the first datastep iteration
then bb in the second
then cc in the third.
I think you should post an example of your starting data and the desired output.
It almost sounds like you may want to use an array but setting values based on position in a dataset ( using _n_) is a tad odd.
I agree with ballardw, it seems like a straightforward array application:
data want;
set have;
array varlist {3} aa bb cc;
value_of_uu = varlist{_n_};
run;
There are items to consider. As with all arrays, the elements (aa, bb, and cc) must all be character (or must all be numeric). And if _n_ would ever be greater than 3, the code will generate an error. You can't let the index of the array (_n_) exceed the number of elements in the array (3 for this example).
I agree with @ballardw, the request is quite odd. You can do it, quite easily, but I don't understand why you want to:
data _null_; set aaaa end=last; if _n_=1 then call execute('data want; set aaaa; '); call execute(cat(' ',strip(uu),'="',strip(vv),'";'); if last then call execute(';run;'); run;
This assumes all character. Why though is the real question.
Edit, for @Astounding, you could modify mine above to handle numbers/characters, and check existence and such like - its one of the benefits of generated code over arrays.
deleted
I didn't see you were call executing an entire datastep from the first data step
Never done this. But I tried your code (with adaptations to work with previous examples)
data bbbbb;
set aaaaa end=last;
if _n_=1 then call execute('data want; set aaaaa; ');
call execute(cat(' ',strip(uuu),'="something";'));
if last then call execute(';run;');
run;
And I think it works, I need to check if I can incorporate this idea in my larger problem
NOTE: CALL EXECUTE generated line.
1 + data want; set aaaaa;
2 The SAS System 13:31 Tuesday, May 31, 2016
2 + aa="something";
3 + bb="something";
4 + cc="something";
5 + dd="something";
6 + ee="something";
7 + ff="something";
8 + ;run;
Thanks
It wouldn't be practical in my situation because my datastep is hundreds of lines long and It would be a mess to write call execute at every line.
But it's definitely a working solution.
Maybe I will write another post with the whole problem.
Thanks again!
PROC TRANSPOSE can use one variable to have the name and another to have the value.
proc transpose data=aaaaa out=want ;
id uuu;
var vvv;
run;
This will create varables named AA, BB, ... with values 'gg','hh',....
I need it to be in a datastep
because i'm using hash tables and do loops
%macro dummy();
data DALY1;
*** set lengths ;
length Germ $10 Category1 $50 Category2 $50 AgeGroupDALY $10 Gender $2 value 8 statesList$999;
*** make link to hash tables ;
if _n_=1 then do;
***modelvalues ----------------;
declare hash h1(dataset:'modelData');
h1.definekey ('Germ', 'Category1', 'Category2', 'AgeGroupDALY', 'Gender') ;
h1.definedata('Value');
h1.definedone();
call missing(Germ, Value, Category1, Category2);
***states ---------------------;
declare hash h2(dataset:'states');
h2.definekey ('Germ') ;
h2.definedata('statesList');
h2.definedone();
end;
set DALY_agregate;
put "°°°°° _n_=" _n_;
***get statesList;
rc2=h2.find(KEY:Germ);
put "statesList=" statesList;
***iterate statesList;
do i=1 to countw(statesList);
put "=== i=" i;
***get state from statesList;
state = scan(statesList,i);
put "state=" state;
*>>> create variable with the value of state <<<-------------------------------------------------------- ;
***iterate propertyList;
put "propertyList=&propertyList";
do j=1 to countw("&propertyList");
put "- j=" j;
***get property from &propertyList;
property = scan("&propertyList",j);
put "property=" property;
***get value;
put Germ "-" state "-" property "-" AgeGroupDALY "-" Gender;
rc1=h1.find(KEY:Germ, KEY:state, KEY:property, KEY:AgeGroupDALY, KEY:Gender);
put "value=" value;
duration =
end; ***end iterate propertyList;
end; ***end iterate statesList;
***clean dataset;
drop i j;
***this is another attempt with macro variables;
%do k=1 %to %sysfunc(countw(&statesList)); *e.g. acute_1 asymptomatic_1 ...;
%let state = %scan(&statesList, &k);
put "=== &k &state";
&state = 1; * multiplication of terms ;
put "propertyList=&propertyList";
%do i=1 %to %sysfunc(countw(&propertyList)); *e.g. Severity Duration Probability;
%let property = %scan(&propertyList, &i);
put "-- &i &property";
* set value with lookup ;
rc=h1.find(KEY:Germ, KEY:"&state", KEY:"&property", KEY:AgeGroupDALY, KEY:Gender);
* IF MISSING --> 1 , no weight *;
if rc ^= 0 then value = 1;
if value = . then value = 1;
* IF DURATION = -1 --> take the SPMA Life Expectancy ;
if index(LOWCASE("&property"),'duration') ge 1 then do;
if value=-1 then do;
value = input(put(cats(Gender,'_',AgeGroupSpma),Gender_AG2SPMA2013_.),10.5);
end;
end;
* IF FATAL then take GBD2010;
if index(LOWCASE("&state"),'fatal') ge 1 then do;
if index(LOWCASE("&property"),'severity') ge 1 then do;
value=1;
end;
if index(LOWCASE("&property"),'duration') ge 1 then do;
*put 'YLL======================================';
value = input(put(cats(Gender,'_',AgeGroupDALY),Gender_AG2GBD2010_.),10.5);
*value = 99;
end;
end;
&state._&property = value;
&state = &state * value;
%end;
%end;
run;
%mend dummy;
%dummy;
You need to post examples of the data in and data wanted out. For example what do two datasets (modelData and states) you are loading into hash tables look like? What does the dataset, DALY_agregate, that is driving the data step look like? What do you want the DALY1 dataset to look like?
Please post in the form of a data step that others can run. You can simplify to make it easier to post.
SAS Innovate 2025 is scheduled for May 6-9 in Orlando, FL. Sign up to be first to learn about the agenda and registration!
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.
Ready to level-up your skills? Choose your own adventure.