BookmarkSubscribeRSS Feed
🔒 This topic is solved and locked. Need further help from the community? Please sign in and ask a new question.
Mina-sh
Fluorite | Level 6

Hello,

I'm using SAS 9.3.1 and I am trying to assign the values of a variable (demand) from a file (a) to a new set of variables using do loops. The problem is that the file 'a' has 5 observations and therefore after the first execution it reads all the data perfectly. But for the second round (i=2) it cannot perform the same task and start reading the file 'a' just like the previous iteration. It is like when a file is read once cannot be read for the second time. As the result, I don't have the desired outputs for the second run. Please note that the program executes without showing any error.   

I'm forwarding you the whole file in which you can find this specific part with all data example I'm using. 

I do appreciate your time helping me to find out the problem.

 

Best Regards,

Mina

 

do i=1 to 2;
_type_='GE';
_row_='Res_P'||put(i,1.);
_col_='_RHS_';
_coef_=0;
output;
_type_=' ';
do k=1 to 4;
_col_='Y'||put(i,1.)||put(k,1.);
_coef_=1.0;
output;
end;
do h=1 to 5;
set a;
_col_='Z'||put(i,1.)||put(h,1.);
_coef_=1.0;
output;
_col_='S'||put(i,1.)||put(h,1.);
_coef_=-demand;
output;

end;
end;

1 ACCEPTED SOLUTION

Accepted Solutions
ballardw
Super User

You may want to consider using some of the concatenation functions. In stead of

 

_col_='Z'||put(i,1.)||put(h,1.);

 

could use

_col_ = cats('Z',i,h);

 

CATS removes leading and trailing blanks. The || put(var, format.) will often have either leading or trailing blanks..

View solution in original post

9 REPLIES 9
Astounding
PROC Star

The solution is simple (I think!), but comes with a warning.  Change the SET statement to become:

 

set a point=h;

 

POINT= tells the software which observation to bring in, but allows for moving back to the beginning and starting over again.

 

The warning:  by doing this, you may create an infinite loop.  While you haven't posted the entire DATA step, so it's impossible to be certain, you will likely need to add a STOP statement at the bottom of the DATA step to make sure it ends.

Mina-sh
Fluorite | Level 6

 Thank you so much, this idea should work... I'm very new in SAS, sorry for asking basic questions... what value then I need to use to start from the beginning when it ends reading the file?

Astounding
PROC Star

The interior DO loop uses:

 

do h=1 to 5;

 

So this automatically starts from the beginning because it uses H to choose which observation to read:

 

set have point=H;

Mina-sh
Fluorite | Level 6

I do appreciate you. I added the point=H to the set statement as an option:

set a point=H;

But it seems like I got stuck in a loop... should I add/change something else? This way it doesn't work...

Astounding
PROC Star

Yes.  When using point=, there often is no ending to the DATA step.  You have to add your own ending by adding a STOP statement.  I thought I pointed this out in my original response, but it's probably a lot to absorb at one time.  Nothing like experience to ingrain the knowledge though.

RW9
Diamond | Level 26 RW9
Diamond | Level 26

Hi,

 

Well, firstly the code you give is very confusing.  It is really not a good idea to call your variables _xyz_ as these types of things are reserved for SAS core functionality.  

Now looking at the output, it all seems a bit overcomplicated - there is lots being created here for no apparent reason or logic, therefore any work you do further on this data will be far harder.  I am presuming its for a report?  

Anyways, as the basis is demand, and you create a bunch of observations for each obs in demand, set that as your base loop:

data modified;
  set demand;
  _row_=cats("Res_P",put(customer,best.));
  _col_="_RHS_";
  _coef_=0;
  output;
  do i=10 to 14;
    _col_=cats("Y",put(i,best.));
    _coef_=1;
    output;
  end;
  do i=11 to 15;
    _col_=cats("Z",put(i,best));
    _coef_=...;
    output;
    _col_=cats("S",put(i,best.));
    _coef_=...;
    output;
  end;
run;

Here, instead of doing some creation, then later setting the data in a loop, I use the demand dataset and for each observation output a bunch of rows.  Seems simpler to me, but then as I say the whole structure and purpose of this output is a total mystery to my, or why you would want to do things in this manner?

Mina-sh
Fluorite | Level 6

Thank you so much. You are right, this structure is weird and I don't like it either, but I have to adhere to that to prepare my data for the proc lp (for SAS OR)... I cannot change the counter because I need to write it there... 

ballardw
Super User

You may want to consider using some of the concatenation functions. In stead of

 

_col_='Z'||put(i,1.)||put(h,1.);

 

could use

_col_ = cats('Z',i,h);

 

CATS removes leading and trailing blanks. The || put(var, format.) will often have either leading or trailing blanks..

Mina-sh
Fluorite | Level 6

Oh! thank you so much for giving me this point. This will be really helpful.

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!

What is Bayesian Analysis?

Learn the difference between classical and Bayesian statistical approaches and see a few PROC examples to perform Bayesian analysis in this video.

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
  • 9 replies
  • 1884 views
  • 4 likes
  • 4 in conversation