BookmarkSubscribeRSS Feed
🔒 This topic is solved and locked. Need further help from the community? Please sign in and ask a new question.
dustychair
Pyrite | Level 9

Hi all,

Although I understand the pattern/idea of formula I don't know how to write it with arrays. For example for p_m1 the equation is,

 

p_m1=(ex1_1/sumex1)*(ex3_1/sumex3) + (ex1_2/sumex1)*(ex3_2/sumex3) + (ex1_3/sumex1)*(ex3_3/sumex3) + (ex1_4/sumex1)*(ex3_4/sumex3)

 

For p_m2 it is,

 

p_m2=(ex1_1/sumex1)*(ex2_1/sumex2) + (ex1_2/sumex1)*(ex2_2/sumex2) + (ex1_3/sumex1)*(ex2_3/sumex2) + (ex1_4/sumex1)*(ex2_4/sumex2)

 

and lastly for p_m3 it is,

 

p_m3= (ex2_1/sumex2)*(ex3_1/sumex3) + (ex2_2/sumex2)*(ex3_2/sumex3) + (ex2_3/sumex2)*(ex3_3/sumex3) + (ex2_4/sumex2)*(ex3_4/sumex3)

 

I'll appreciate you if you help me to write these codes with arrays/loops whatever I need.

Thank you

 

My code:

 

data all_pars1;
set all_pars (obs=20);;
array t {3} theta1-theta3 ;
array ex {3,4} &vlist;
array s {4};
array inc {4};
array sumex{3} 8.;
array p_m{4} ;
do i=1 to 3;
do j=1 to 4;
ex(i,j)=exp(t(i)*s(j)+inc(j));
sumex{i}=sum(sumex{i},ex{i,j});
p_m{j}=..........................
end;
end;
run;

1 ACCEPTED SOLUTION

Accepted Solutions
KachiM
Rhodochrosite | Level 12

Gocersah,

 

I looked into your code (all_pars1). Instead of rewriting my code to suit you, I thought that you would be much helped if I can find the mistakes and suggest a change. Before we go to your code, I suggest some tips in using Arrays.

 

[1] Use _temporary_ arrays when Variables are not needed in the PDV (Program Data Vector). Simply remember that such variables that do not go to OUTPUT Data Set be used in _temporary_ arrays -- which are used for intermediate computations.

 

[2] Use square brackets('[ ]') instead of braces('{ }') or parentheses( '(  )' ). Both '{' and '(' require two key presses but square bracket requires one key press. Besides it can always be used for arrays everywhere in SAS (eg FCMP). Stick to one of it but don't mix them in a program. See your program for the mixed usage.

 

Now your program. See whether your issue is fixed and the p_m[i] are OK.

 

data all_pars1;
   set all_pars (obs=2); * (obs=20);;
   array t {3} theta1-theta3 ;
   array ex {3,4} &vlist;
   array s {4};
   array inc {4];
   array sumex{3} 8.;
   *array p_m{4} ;
   array p_m{3} ;
   do i=1 to 3;
      do j=1 to 4;
         ex(i,j)=exp(t(i)*s(j)+inc(j));
         sumex{i}=sum(sumex{i},ex{i,j});
         *ex(i,j)=exp(t(i)*s(j)+inc(j));
         *sumex{i}=sum(sumex{i},ex{i,j});
         *p_m(i)=sum((ex{i,j}/sumex{i})*(ex{i,j}/sumex{j}));
         p_m(i)=sum((ex{i,j}/sumex{i})*(ex{i,j}/sumex{i}));
      end;
      put p_m[i] =;
   end;
run;

Best of luck.

DATAsp

 

 

 

 

View solution in original post

10 REPLIES 10
Kurt_Bremser
Super User

One index value goes 1-1-2, the other 3-2-3. The code needed to derive those values from the 1-2-3 sequence of a possible do loop might cause enough obfuscation to offset the gain by using only one formula line with arrays.

Astounding
PROC Star
Because of the changing patterns to the variable names, arrays would be a poor tool for the job. If it is valuable to you to build job security by complicating the code, you could use 3 calls to a macro. For example, a macro call to compute p_m1 would look something like this:

%compute (1,1_1,1,3_1,3,1_2,1,3_2,3,1_3,1,3_3,3,1_4,1,3_4,3)

And there are questions to clear up first about the variable names, before even trying to write such a macro. Does this sound like it would be worthwhile to you?
KachiM
Rhodochrosite | Level 12

Hi Gocersah,

 

Arrays can be used but not directly. I give you an array solution as much as I understand your problem.

The steps are:

[1] Hold the values of ex1_1 ... ex1_4 in an array.

[2] Similarly, hold ex2_.., ex3_ in separate arrays.

[3] Hold sumex1, sumex2 and sumex3 in another array.

 

I used some fictional values for the cells of the arrays and computed p_m1, p_m2 and p_m3. I place the intermediate values computed from the arrays in the LOG.

data _null_;
array ex1[4] _temporary_ (10,20,30,40);
array ex2[4] _temporary_ (20,30,40,50);
array ex3[4] _temporary_ (30,40,50,60);
array sumex[3] _temporary_  (5,10,10);

do i = 1 to dim(ex1);
   ex1[i] = ex1[i] / sumex[1];
   ex2[i] = ex2[i] / sumex[2];
   ex3[i] = ex3[i] / sumex[3];
   put ex1[i] = ex2[i] = ex3[i] =;
end;
p_m1 = 0; p_m2 = 0; p_m3 = 0;
do i = 1 to dim(ex1);
p_m1 = p_m1 + ex1[i] * ex3[i];
p_m2 = p_m2 + ex1[i] * ex2[i];
p_m3 = p_m3 + ex2[i] * ex3[i];
end;
put p_m1 = p_m2 = p_m3= ;  
run;

 On the Log:

 ex1[1]=2 ex2[1]=2 ex3[1]=3
 ex1[2]=4 ex2[2]=3 ex3[2]=4
 ex1[3]=6 ex2[3]=4 ex3[3]=5
 ex1[4]=8 ex2[4]=5 ex3[4]=6
 p_m1=100 p_m2=80 p_m3=68

The original values in the arrays ex1[ ], ex2[ ], ex3[ ] are modified in place by the appropriate division of sumx:

Then the  product sums are simply the product of two parallel columns.

 

Best regards,

DATAsp

dustychair
Pyrite | Level 9

Hi @KachiM,

I did try your code. Actually I don't know whether the order of statements important or not, but I placed your code into my existing code. I got an error says that p_m is out of range. I guess it is a simple error to be fixed. 

Here is all of my code and my input files  are attached. My all code will be more helpful to explain what I mean since I might not use proper terms.

I appreciate for your help.

data par;
infile 'C:\cluster_new\mlg1.txt';
input a1 a2 a3 b1 b2 b3 ;
run;
data score;
infile 'C:\cluster_new\mlgs.txt';
input theta1 theta2 theta3;
run;
data all_pars;
if _n_=1 then set score;
set par;
run;
data all_pars;
set all_pars;
s1=-(a1+a2+a3)/4;
s2=s1+a1;
s3=s1+a2;
s4=s1+a3;
inc1=-(b1+b2+b3)/4;
inc2=inc1+b1;
inc3=inc1+b2;
inc4=inc1+b3;
run;
data _null_;
length c $16000; /* 500*4*(up to 😎 characters: " ex123_4" */
do i=1 to 3;
do j=1 to 4;
c=catx(' ',c,cats('ex',i,'_',j));
end;
end;
call symputx('vlist',c);
run;
data _null_;
array ex1[4] _temporary_ (10,20,30,40);
array ex2[4] _temporary_ (20,30,40,50);
array ex3[4] _temporary_ (30,40,50,60);
array sumex[3] _temporary_ (5,10,10);

do i = 1 to dim(ex1);
ex1[i] = ex1[i] / sumex[1];
ex2[i] = ex2[i] / sumex[2];
ex3[i] = ex3[i] / sumex[3];
put ex1[i] = ex2[i] = ex3[i] =;
end;
p_m1 = 0; p_m2 = 0; p_m3 = 0;
do i = 1 to dim(ex1);
p_m1 = p_m1 + ex1[i] * ex3[i];
p_m2 = p_m2 + ex1[i] * ex2[i];
p_m3 = p_m3 + ex2[i] * ex3[i];
ex1[1]=2 ex2[1]=2 ex3[1]=3
ex1[2]=4 ex2[2]=3 ex3[2]=4
ex1[3]=6 ex2[3]=4 ex3[3]=5
ex1[4]=8 ex2[4]=5 ex3[4]=6
p_m1=100 p_m2=80 p_m3=68
end;
put p_m1 = p_m2 = p_m3= ;
run;
data all_pars1;
set all_pars (obs=20);;
array t {3} theta1-theta3 ;
array ex {3,4} &vlist;
array s {4};
array inc {4};
array sumex{3} 8.;
array p_m{4} ;
do i=1 to 3;
do j=1 to 4;
ex(i,j)=exp(t(i)*s(j)+inc(j));
sumex{i}=sum(sumex{i},ex{i,j});
ex(i,j)=exp(t(i)*s(j)+inc(j));
sumex{i}=sum(sumex{i},ex{i,j});
p_m(i)=sum((ex{i,j}/sumex{i})*(ex{i,j}/sumex{j}));
end;
end;
run;

KachiM
Rhodochrosite | Level 12

Gocersah,

 

I looked into your code (all_pars1). Instead of rewriting my code to suit you, I thought that you would be much helped if I can find the mistakes and suggest a change. Before we go to your code, I suggest some tips in using Arrays.

 

[1] Use _temporary_ arrays when Variables are not needed in the PDV (Program Data Vector). Simply remember that such variables that do not go to OUTPUT Data Set be used in _temporary_ arrays -- which are used for intermediate computations.

 

[2] Use square brackets('[ ]') instead of braces('{ }') or parentheses( '(  )' ). Both '{' and '(' require two key presses but square bracket requires one key press. Besides it can always be used for arrays everywhere in SAS (eg FCMP). Stick to one of it but don't mix them in a program. See your program for the mixed usage.

 

Now your program. See whether your issue is fixed and the p_m[i] are OK.

 

data all_pars1;
   set all_pars (obs=2); * (obs=20);;
   array t {3} theta1-theta3 ;
   array ex {3,4} &vlist;
   array s {4};
   array inc {4];
   array sumex{3} 8.;
   *array p_m{4} ;
   array p_m{3} ;
   do i=1 to 3;
      do j=1 to 4;
         ex(i,j)=exp(t(i)*s(j)+inc(j));
         sumex{i}=sum(sumex{i},ex{i,j});
         *ex(i,j)=exp(t(i)*s(j)+inc(j));
         *sumex{i}=sum(sumex{i},ex{i,j});
         *p_m(i)=sum((ex{i,j}/sumex{i})*(ex{i,j}/sumex{j}));
         p_m(i)=sum((ex{i,j}/sumex{i})*(ex{i,j}/sumex{i}));
      end;
      put p_m[i] =;
   end;
run;

Best of luck.

DATAsp

 

 

 

 

dustychair
Pyrite | Level 9

So, no need to write the below part anymore? I did try the new code.I didn't get any errors but the results are different than what I have in excel.Expected p_m results are: 

 

0.30      0.27      0.31      

0.35      0.31      0.38      

0.35      0.33      0.35      

(just first three rows of excel)

 

Thank you SO much!

 

data _null_;
array ex1[4] _temporary_ (10,20,30,40);
array ex2[4] _temporary_ (20,30,40,50);
array ex3[4] _temporary_ (30,40,50,60);
array sumex[3] _temporary_ (5,10,10);

do i = 1 to dim(ex1);
ex1[i] = ex1[i] / sumex[1];
ex2[i] = ex2[i] / sumex[2];
ex3[i] = ex3[i] / sumex[3];
put ex1[i] = ex2[i] = ex3[i] =;
end;
p_m1 = 0; p_m2 = 0; p_m3 = 0;
do i = 1 to dim(ex1);
p_m1 = p_m1 + ex1[i] * ex3[i];
p_m2 = p_m2 + ex1[i] * ex2[i];
p_m3 = p_m3 + ex2[i] * ex3[i];
end;
put p_m1 = p_m2 = p_m3= ;
run;

KachiM
Rhodochrosite | Level 12

Please check the statement you wrote in SAS with EXCEL for p_m[i]. In SAS it is a SUM of squares. Also other statements too.

Probably, you might have missed in the translation of Excel to SAS.

DATAsp

dustychair
Pyrite | Level 9

@KachiM  Thank you SO much!

KachiM
Rhodochrosite | Level 12

Hi Gocersah,

 

I gave a solution on Sunday on what I thought you want. Perhaps it didn't help you. I appreciate that you respond to this. Tell us any issues with the solution offered.

 

DATAsp

dustychair
Pyrite | Level 9

Hi @KachiM ,

I'm so sorry. Since I have posted another question, I did not notice your response. I'll try it and let you know as soon as I go home. 

I appreciate for your response for your help.

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!

Mastering the WHERE Clause in PROC SQL

SAS' Charu Shankar shares her PROC SQL expertise by showing you how to master the WHERE clause using real winter weather data.

Find more tutorials on the SAS Users YouTube channel.

Discussion stats
  • 10 replies
  • 2715 views
  • 7 likes
  • 4 in conversation