DATA Step, Macro, Functions and more

Finding values using a loop

Accepted Solution Solved
Reply
Super Contributor
Posts: 272
Accepted Solution

Finding values using a loop

[ Edited ]

Dear sir,

 

I am having little difficult in my code using array statement. I am using the following code. I am having trouble in concatenation part of my code. Please help where is wrong in my code.

 

Thanks

 

data one;
input AESER $ AESDTH $ AESLIFE $ AESHOSP $ AESCONG $ AESDISAB $ AESMIE $ INFECDIS $;
datalines;
N N N N N N N N
Y N N N N N N N
Y Y N N N N N N
Y Y N N N N N N
;
run;
data two;
length aesern $20;
set one;
if AESER = 'N' THEN AESERN = 'No';
array AESP {7} $ AESDTH AESLIFE AESHOSP AESCONG AESDISAB AESMIE INFECDIS;
do i = 1 to 7;
if AESER = 'Y' and AESP (i) = 'N' then AESERN = 'Yes';
if AESER = 'Y' and AESP (i) = 'Y' then AESERN= 'Yes'||''||compress('('||i||')');;
end;
run;

 

OUTPUT:

AESERN value for observations 2-4 is 'YES'. But I am expecting' YES  (1) ' for 3 and 4 observations. why the concatenation part not working.

 


Accepted Solutions
Solution
‎06-15-2016 01:44 AM
Super User
Posts: 19,771

Re: base

Posted in reply to knveraraju91

Trace your code. 

 

Lets look at line 5 of your data

 

i=1 & second if statement is true so you set variable = Yes (1)

i=2 & second if condition is true so you set variable = Yes (2) 

At this point you've already overwritten your original variable. 

 

You logic inside the loop isn't what you want. 

 

Try looping through and creating a list of cases where you find your Y. Then check it against first condition and append the Yes portion and your list. 

 

I would recommend pseudocoding it for yourself first and then trying to program it. It's not a difficult problem but it's not trivial either and you'll learn more. 

 

View solution in original post


All Replies
Super Contributor
Posts: 266

Re: base

Posted in reply to knveraraju91

You changed the query by the time I came back to answer. Smiley Happy 

PROC Star
Posts: 1,759

Re: base

[ Edited ]
Posted in reply to knveraraju91

You always execute the loop until I=7 and the values are N for I=7.

 

If you need to keep the match for Y, you must exit the loop when you find it.

 


data TWO;
  length AESERN $20;
  set ONE;
  array AESP {7} $ AESDTH -- INFECDIS;
  if AESER = 'N' then AESERN = 'No';
  else do I = 1 to 7;
    if AESP (I) = 'Y' then do;
      AESERN= cats('Yes(',I,')');
      leave;
    end;
    else AESERN = 'Yes';
  end;
run;

 

PROC Star
Posts: 1,759

Re: base

You can also write this like:

 


data TWO;
  length AESERN $20;
  set ONE;
  array AESP {7} $ AESDTH -- INFECDIS;
  FIND_Y = whichc('Y', of AESP[*]);
  AESERN = ifc( AESER = 'N' 
              , 'No'
              , 'Yes' || ifc(FIND_Y, cats('(',FIND_Y,')'), ''));
run;
Super Contributor
Posts: 272

Re: base

Thank you. That helped me. But there is one issue that this code is not getting the right output.

 

For observation 5, I suppose to get the out put like this "Yes (1,6)".  But I am getting  "Yes (1)". Please help in the code. Thank you

 

data one;
input AESER $ AESDTH $ AESLIFE $ AESHOSP $ AESCONG $ AESDISAB $ AESMIE $ INFECDIS $;
datalines;
N N N N N N N N
Y N N N N N N N
Y Y N N N N N N
Y Y N N N N N N

Y Y Y N N N N N
;
run;
data two;
length aesern $20;
set one;
if AESER = 'N' THEN AESERN = 'No';
array AESP {7} $ AESDTH AESLIFE AESHOSP AESCONG AESDISAB AESMIE INFECDIS;
do i = 1 to 7;
if AESER = 'Y' and AESP (i) = 'N' then AESERN = 'Yes';
if AESER = 'Y' and AESP (i) = 'Y' then AESERN= 'Yes'||''||compress('('||i||')');;
end;
run;

 

OUTPUT:

AESERN value for observations 2-4 is 'YES'. But I am expecting' YES  (1) ' for 3 and 4 observations. why the concatenation part not working.

 

 

PROC Star
Posts: 1,759

Re: base

Posted in reply to knveraraju91
Super Contributor
Posts: 272

Re: base

Observation 5 has two 'Y' other than for AESER. One for AESDTH and another for AESLIFE. In array statement AESDTH =1 and AESLIFE=2. So, my output should be "Yes (1,2)" .I have to concatenate both values to YES. Thank you for your help.

 

 

For observation 5, I suppose to get the out put like this "Yes (1,6)". But I am getting "Yes (1)". Please help in the code. Thank you

data one;
input AESER $ AESDTH $ AESLIFE $ AESHOSP $ AESCONG $ AESDISAB $ AESMIE $ INFECDIS $;
datalines;
N N N N N N N N
Y N N N N N N N
Y Y N N N N N N
Y Y N N N N N N
Y Y Y N N N N N
;
run;
data two;
length aesern $20;
set one;
if AESER = 'N' THEN AESERN = 'No';
array AESP {7} $ AESDTH AESLIFE AESHOSP AESCONG AESDISAB AESMIE INFECDIS;
do i = 1 to 7;
if AESER = 'Y' and AESP (i) = 'N' then AESERN = 'Yes';
if AESER = 'Y' and AESP (i) = 'Y' then AESERN= 'Yes'||''||compress('('||i||')');;
end;
run;

OUTPUT:
AESERN value for observations 2-4 is 'YES'. But I am expecting' YES (1) ' for 3 and 4 observations. why the concatenation part not working.

PROC Star
Posts: 1,759

Re: base

Posted in reply to knveraraju91

Please do not copy all the text each time as your replies become mixed with your previous (erroneous in this case) replies.

 

Try this:


data TWO;
  length AESERN $20;
  set one;
  array AESP {7} $ AESDTH -- INFECDIS;
  array POS  {7} $1 ;
  drop I POS:;
  AESERN =ifc( AESER = 'N' , 'No', 'Yes');
  if AESERN = 'Yes' and whichc('Y', of AESP[*]) then do;
    do I = 1 to 7;
      if AESP[I]='Y' then POS[I]=cat(I);  
    end;
    AESERN = cats(AESERN, '(', catx(',', of POS[*]), ')');
  end;
run;
Super Contributor
Posts: 272

Re: base

Thank you so much

Super User
Posts: 19,771

Re: base

Posted in reply to knveraraju91

@knveraraju91 @ChrisNZ has provided the correct answer, not me. 

PROC Star
Posts: 1,759

Re: base

Cheers @Reeza . Life isn't fair is it?  Smiley Happy

Super Contributor
Posts: 272

Re: base

Hi,

 

Thank you for the help. I have one more thing I need help in the code if you can.

 

The out put produced as expected, but I need one more modifification.

 

With your code I am getting out for 3,4,5 observation is= Yes(1) and Yes(1,2).  But I need a gap between YES and the parenthesis.

 

eg: I need output ike this: Yes (1) and Yes (1,2).

 

Thank you

PROC Star
Posts: 1,759

Re: base

[ Edited ]
Posted in reply to knveraraju91

Really?

 

People here don't help you to do your job for you, but to show you so you can learn.

 

This is a trivial change when the final concatenation takes place. Please understand the few lines of code and change them accordingly.

Super Contributor
Posts: 272

Re: base

I always post a question as a last option after not finding any answer. I also learn new things from the forum. You guys are really great. Thanks.

Solution
‎06-15-2016 01:44 AM
Super User
Posts: 19,771

Re: base

Posted in reply to knveraraju91

Trace your code. 

 

Lets look at line 5 of your data

 

i=1 & second if statement is true so you set variable = Yes (1)

i=2 & second if condition is true so you set variable = Yes (2) 

At this point you've already overwritten your original variable. 

 

You logic inside the loop isn't what you want. 

 

Try looping through and creating a list of cases where you find your Y. Then check it against first condition and append the Yes portion and your list. 

 

I would recommend pseudocoding it for yourself first and then trying to program it. It's not a difficult problem but it's not trivial either and you'll learn more. 

 

☑ This topic is solved.

Need further help from the community? Please ask a new question.

Discussion stats
  • 14 replies
  • 432 views
  • 4 likes
  • 4 in conversation