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

Hi, 

 

I hope someone is able to help me with below.

 

I have two datasets: Dataset 1 contains raw data for a number of variables and dataset 2 contains a set of weights for the same variables. Example is shown below: 

 

Dataset 1: Raw data

ABCD
8247
1356
73310
4375
1678
4179
2712
181010
77610

 

Dataset 2: weights

BADC
0.20.30.10.4

 

I would like to multiply all observations A in dataset 1 with the weight A in dataset 2. The same goes for variables B, C and D. The variables are though not listed in the same order. Can someone please help me with this?

*** Actual dataset contains a large number of variables, so solutions without manual calculation for each variable would be greatly appreciated***

1 ACCEPTED SOLUTION

Accepted Solutions
yabwon
Onyx | Level 15

Hi,

 

try this:

 

data Dataset1;
input A	B	C	D;
cards;
8	2	4	7
1	3	5	6
7	3	3	10
4	3	7	5
1	6	7	8
4	1	7	9
2	7	1	2
1	8	10	10
7	7	6	10
;
run; 

data Dataset2;
input B	A	D	C;
cards;
0.2	0.3	0.1	0.4
;
run;

data want;
  if 0 then set Dataset1; /* set vars order */

  array vars A--D;
  array weights[4] _temporary_;

  set Dataset2;
  do _I_ = lbound(vars) to hbound(vars); /* create temporary weights */
    weights[_I_] = vars[_I_] ;
  end;

  do until(eof); /* loop over dataset */
    set Dataset1 end=eof;

    do _I_ = lbound(vars) to hbound(vars); /* update values */
      vars[_I_] = vars[_I_] * weights[_I_];
    end;
    output;
  end;

  stop;
run;

 

All the best

Bart

_______________
Polish SAS Users Group: www.polsug.com and communities.sas.com/polsug

"SAS Packages: the way to share" at SGF2020 Proceedings (the latest version), GitHub Repository, and YouTube Video.
Hands-on-Workshop: "Share your code with SAS Packages"
"My First SAS Package: A How-To" at SGF2021 Proceedings

SAS Ballot Ideas: one: SPF in SAS, two, and three
SAS Documentation



View solution in original post

10 REPLIES 10
sustagens
Pyrite | Level 9
proc sql;
create table want as 
select 
a * (select a from ds2) as product_a,
b * (select b from ds2) as product_b,
c * (select c from ds2) as product_c,
d * (select d from ds2) as product_d 
from ds1;
quit;
Birgithj
Fluorite | Level 6

Thank you for your answer. 

Do you know if this can be done without writing each calculation manually? I ask because I have a dataset containing 90 variables, and manual calculation will be very time consuming. 

yabwon
Onyx | Level 15

Hi,

 

try this:

 

data Dataset1;
input A	B	C	D;
cards;
8	2	4	7
1	3	5	6
7	3	3	10
4	3	7	5
1	6	7	8
4	1	7	9
2	7	1	2
1	8	10	10
7	7	6	10
;
run; 

data Dataset2;
input B	A	D	C;
cards;
0.2	0.3	0.1	0.4
;
run;

data want;
  if 0 then set Dataset1; /* set vars order */

  array vars A--D;
  array weights[4] _temporary_;

  set Dataset2;
  do _I_ = lbound(vars) to hbound(vars); /* create temporary weights */
    weights[_I_] = vars[_I_] ;
  end;

  do until(eof); /* loop over dataset */
    set Dataset1 end=eof;

    do _I_ = lbound(vars) to hbound(vars); /* update values */
      vars[_I_] = vars[_I_] * weights[_I_];
    end;
    output;
  end;

  stop;
run;

 

All the best

Bart

_______________
Polish SAS Users Group: www.polsug.com and communities.sas.com/polsug

"SAS Packages: the way to share" at SGF2020 Proceedings (the latest version), GitHub Repository, and YouTube Video.
Hands-on-Workshop: "Share your code with SAS Packages"
"My First SAS Package: A How-To" at SGF2021 Proceedings

SAS Ballot Ideas: one: SPF in SAS, two, and three
SAS Documentation



PeterClemmensen
Tourmaline | Level 20
data one;
input A B C D;
datalines;
8 2 4 7
1 3 5 6
7 3 3 10
4 3 7 5
1 6 7 8
4 1 7 9
2 7 1 2
1 8 10 10
7 7 6 10
;
 
data two;
input B A D C;
datalines;
0.2 0.3 0.1 0.4
;

proc sql noprint;
    select name into :n separated by ' '
    from dictionary.columns
    where libname='WORK' and upcase(memname)=upcase('one');
quit;

data v_two / view=v_two;
    format &n.;
    set two;
run;

data want(drop=i j lr);
    format &n.;

    array v {4} &n.;
    array w {4} _temporary_;

    set v_two;
    do i=1 to dim(w);
        w[i]=v[i];
    end;

    do until (lr);
        set one;
        do j=1 to dim(v);
            v[j]=v[j]*w[j];
        end;
        output;
    end;
run;

Result:

 

A    B    C    D
2.4  0.4  1.6  0.7
0.3  0.6  2 0. 6
2.1  0.6  1.2  1
1.2  0.6  2.8  0.5
0.3  1.2  2.8  0.8
1.2  0.2  2.8  0.9
0.6  1.4  0.4  0.2
0.3  1.6  4    1
2.1  1.4  2.4  1
PeterClemmensen
Tourmaline | Level 20

Just for fun

 

data _two;
    if 0 then set one nobs=nobs;
    do i=1 to nobs;
        set two point=_N_;
        output;
    end;
    stop;
    drop i;
run;

proc fcmp; 
    array _1   {9, 4} / nosymbols;
    array _2   {9, 4} / nosymbols;
    array want {9, 4} / nosymbols;
    rc=read_array('one', _1);
    rc=read_array('_two', _2);
    call elemmult(_1, _2, want);
    rc=write_array('want', want);
run;
yabwon
Onyx | Level 15

Nice one,

 

the only sad thing is you can't do:

data _two / view = _two;

because `read_array` falls...

 

All the best

Bart

 

 

_______________
Polish SAS Users Group: www.polsug.com and communities.sas.com/polsug

"SAS Packages: the way to share" at SGF2020 Proceedings (the latest version), GitHub Repository, and YouTube Video.
Hands-on-Workshop: "Share your code with SAS Packages"
"My First SAS Package: A How-To" at SGF2021 Proceedings

SAS Ballot Ideas: one: SPF in SAS, two, and three
SAS Documentation



PeterClemmensen
Tourmaline | Level 20

@yabwon, yes, seems read_arrar sadly can't handle views.

Ksharp
Super User
data one;
input A B C D;
datalines;
8 2 4 7
1 3 5 6
7 3 3 10
4 3 7 5
1 6 7 8
4 1 7 9
2 7 1 2
1 8 10 10
7 7 6 10
;
 
data two;
input B A D C;
datalines;
0.2 0.3 0.1 0.4
;
proc transpose data=one(obs=0) out=name;
var _all_;
run;
proc sql;
select cats(_name_,'=_',_name_) into : rename separated by ' ' from name;
select cats(_name_,'=',_name_,'*_',_name_) into : multi separated by ';' from name;
quit; 
data want ;
 set one;
 if _n_=1 then set two(rename=(&rename));
 &multi ;
drop _:;
run;
Ksharp
Super User

OR if you have IML which would get you faster .

 

data one;
input A B C D;
datalines;
8 2 4 7
1 3 5 6
7 3 3 10
4 3 7 5
1 6 7 8
4 1 7 9
2 7 1 2
1 8 10 10
7 7 6 10
;
 
data two;
input B A D C;
datalines;
0.2 0.3 0.1 0.4
;

proc iml;
use one;
read all var _all_ into one[c=vname1];
close;

use two;
read all var _all_ into two[c=vname2];
close;

mattrib two c=vname2 r={'x'};
want=one#two['X',vname1];
create want from want[c=vname1];
append from want;
close;
quit;
Astounding
PROC Star

I know it's solved, but found this interesting enough to share:

 

data _null_;
   set dataset2;
   array nums {*} _numeric_;
   call execute ('data want; set dataset1;');
   do k=1 to dim(nums);
      formula = cats(vname(nums{k}), '=' , vname(nums{k}), '*', nums{k}, ';' ) ;
      call execute(formula);
   end;
   call execute('run;');
run;

sas-innovate-2024.png

Available on demand!

Missed SAS Innovate Las Vegas? Watch all the action for free! View the keynotes, general sessions and 22 breakouts on demand.

 

Register now!

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
  • 10 replies
  • 988 views
  • 7 likes
  • 6 in conversation