turn on suggestions

Auto-suggest helps you quickly narrow down your search results by suggesting possible matches as you type.

Showing results for

Find a Community

- Home
- /
- Analytics
- /
- Forecasting
- /
- Abbreviation of long sums in proc model

Topic Options

- Subscribe to RSS Feed
- Mark Topic as New
- Mark Topic as Read
- Float this Topic for Current User
- Bookmark
- Subscribe
- Printer Friendly Page

Highlighted
# Abbreviation of long sums in proc model

Options

- Mark as New
- Bookmark
- Subscribe
- Subscribe to RSS Feed
- Highlight
- Email to a Friend
- Report Inappropriate Content

08-31-2017 02:22 AM

Dear community,

I would be glad, if you were to provide help concerning my following issue.

Core of my question: Is there (an equivalent of) a sum operator in the "proc model" environment?

Explicit setting/example:

I am running the following regression, where I am trying to estimate the an exponential decay function, where y is assumed to be an exponentially weighted sum of lagged x-es.

```
%ODSOff;
proc model
data = in;
endo = y;
exog
x_l1-x_l18;
parms
a
b
l;
mflow =
a +
b * (
exp(-l*(0))*x_l1+
exp(-l*(1))*x_l2+
exp(-l*(2))*x_l3+
exp(-l*(3))*x_l4+
exp(-l*(4))*x_l5+
exp(-l*(5))*x_l6+
exp(-l*(6))*x_l7+
exp(-l*(7))*x_l8+
exp(-l*(8))*x_l9+
exp(-l*(9))*x_l10+
exp(-l*(10))*x_l11+
exp(-l*(11))*x_l12+
exp(-l*(12))*x_l13+
exp(-l*(13))*x_l14+
exp(-l*(14))*x_l15+
exp(-l*(15))*x_l16+
exp(-l*(16))*x_l17+
exp(-l*(17))*x_l18);
fit mflow
/ gmm;
ods output
ParameterEstimates = ParameterEstimates_sine_exp_x
ResidSummary = ResidSummary_sine_exp_x;
run; quit;
%ODSOn;
```

This is the skeleton of the model.

Next, I add covariates.

Among this, there are a many indicator variables.

E.g., I want to use "time dummies".

For the sake of it, please let us assume I do not want to de-mean, I like to have distinct coefficient estimates.

The sample has is that there are 192 time points, i.e. 192 indicator variables, i.e. 191 regressors for my model for I want to keep a, the model's intercept.

As of now, I used a very-quick-and-dirty-way: Generate a list of "t2*month_indicator2 + ... + t192*month_indicator192" conveniently in Excel and copy-paste it.

The code becomes even more messy than it already is.

Thus, I would like to have something like a sum-operator in the vein "sum from i=2 to 192: ti*month_indicatori".

If it is of any importance, I am trying to replicate the method by Barber/Huang/Odean (2016) ("Which Factors Matter to Investors? Evidence from Mutual Fnd Flows") and it is ought to be equation (5).

Yours sincerely

Sinistrum

Accepted Solutions

Solution

08-31-2017
09:50 AM

- Mark as New
- Bookmark
- Subscribe
- Subscribe to RSS Feed
- Highlight
- Email to a Friend
- Report Inappropriate Content

08-31-2017 09:29 AM

You need to put it in a macro. Do the following outside your proc model statement:

```
%macro sum_script();
%do i = 2 %to 191;
t&i.*month_indicator&i. +
%end;
t192*month_indicator192;
%mend;
```

Then call %sum_script; in proc model where you insert the summation function.

All Replies

- Mark as New
- Bookmark
- Subscribe
- Subscribe to RSS Feed
- Highlight
- Email to a Friend
- Report Inappropriate Content

08-31-2017 09:10 AM

Sinistrum, you can use macro statement to generate the summation list:

```
%do i = 2 %to 191;
t&i.*month_indicator&i. +
%end;
t192*month_indicator192
```

The above statement will give you:

`t2*month_indicator2 + t3*month_indicator3 +... + t192*month_indicator192`

Hope this helps.

Thanks,

Pu

- Mark as New
- Bookmark
- Subscribe
- Subscribe to RSS Feed
- Highlight
- Email to a Friend
- Report Inappropriate Content

08-31-2017 09:26 AM - edited 08-31-2017 09:26 AM

Thank you Puwang, but I receive the error 'The %DO statement is not valid in open code.'.

This is how I implemented the idea of yours:

```
%ODSOff;
proc model
data = in;
endo = y;
exog
x_l1-x_l18
month_indicator2-month_indicator192;
parms
a
b
l
t2-t192;
mflow =
a +
b * (
exp(-l*(0))*x_l1+
exp(-l*(1))*x_l2+
exp(-l*(2))*x_l3+
exp(-l*(3))*x_l4+
exp(-l*(4))*x_l5+
exp(-l*(5))*x_l6+
exp(-l*(6))*x_l7+
exp(-l*(7))*x_l8+
exp(-l*(8))*x_l9+
exp(-l*(9))*x_l10+
exp(-l*(10))*x_l11+
exp(-l*(11))*x_l12+
exp(-l*(12))*x_l13+
exp(-l*(13))*x_l14+
exp(-l*(14))*x_l15+
exp(-l*(15))*x_l16+
exp(-l*(16))*x_l17+
exp(-l*(17))*x_l18)
+
/* Your suggestion as I understood */
%do i = 2 %to 191;
t&i.*month_indicator&i. +
%end;
t192*month_indicator192;
fit mflow
/ gmm;
ods output
ParameterEstimates = ParameterEstimates_sine_exp_x
ResidSummary = ResidSummary_sine_exp_x;
run; quit;
%ODSOn;
```

Yours sincereley

Sinistrum

Solution

08-31-2017
09:50 AM

- Mark as New
- Bookmark
- Subscribe
- Subscribe to RSS Feed
- Highlight
- Email to a Friend
- Report Inappropriate Content

08-31-2017 09:29 AM

You need to put it in a macro. Do the following outside your proc model statement:

```
%macro sum_script();
%do i = 2 %to 191;
t&i.*month_indicator&i. +
%end;
t192*month_indicator192;
%mend;
```

Then call %sum_script; in proc model where you insert the summation function.

- Mark as New
- Bookmark
- Subscribe
- Subscribe to RSS Feed
- Highlight
- Email to a Friend
- Report Inappropriate Content

08-31-2017 09:52 AM - edited 08-31-2017 10:01 AM

First, please excuse me for being clumsy,

second, thank you very much indeed.

I can make use of this at so many instances in my codes - I appreciate it a lot.

Yours sincerely

Sinistrum

- Mark as New
- Bookmark
- Subscribe
- Subscribe to RSS Feed
- Highlight
- Email to a Friend
- Report Inappropriate Content

08-31-2017 10:09 AM - edited 08-31-2017 10:12 AM

Glad that I can help.

To make it more convenient, you can just wrap your entire proc model statement (or more code) within a macro, so that you do not need to create extra macros for each %do loop you created.

For example:

```
%macro call_model();
proc model
data = in;
endo = y;
exog
x_l1-x_l18
month_indicator2-month_indicator192;
parms
a
b
l
t2-t192;
mflow =
a +
b * (
%do i = 1 %to 18;
%let j = %eval(&i-1);
exp(-l*(&j))*x_l&i. +
%end;
%do i = 2 %to 191;
t&i.*month_indicator&i. +
%end;
t192*month_indicator192;
fit mflow
/ gmm;
ods output
ParameterEstimates = ParameterEstimates_sine_exp_x
ResidSummary = ResidSummary_sine_exp_x;
run; quit;
%mend;
```

And then call %call_model;

There are also some useful options when you use sas macro, especially useful for debugging:

```
options mprint;
options mlogic;
options symbolgen;
```

The MPRINT option writes to the SAS log each SAS statement generated by a macro.

The MLOGIC option traces the flow of execution of your macro, including the resolution of parameters.

The SYMBOLGEN option tells you what each macro variable resolves to by writing messages to the SAS log.

- Mark as New
- Bookmark
- Subscribe
- Subscribe to RSS Feed
- Highlight
- Email to a Friend
- Report Inappropriate Content

08-31-2017 10:09 AM

PROC MODEL provides many facilities for implementing models like this one. Besides using macros you can use arrays, or the SUM function:

```
proc model ...;
endo y;
exog x1-x10 ind1-ind10;
parms a l t1-t10;
array t[10] t1-t10;
array x[10] x1-x10;
array ind[10] ind1-ind10;
array tmp[10];
do i = 1 to 10;
tmp[i] = exp(-l*(i-1))*x[i]
+ t[i]*ind[i];
end;
y = a + sum (of tmp1-tmp10);
fit y;
quit;
```

- Mark as New
- Bookmark
- Subscribe
- Subscribe to RSS Feed
- Highlight
- Email to a Friend
- Report Inappropriate Content

08-31-2017 10:19 AM

This comes in very handy, thank you very much.

Keeps it all tidied up and in one place in the 'proc model' statement.

I may use multiple 'tmp' as you dubbed them, with different lengths and then fit them together in the actual model equation.

And thank you for elaborating on your answer and given even more hints on how I could improve further, Pu.

Astonishing, how quickly this request has been solved one again.