Statalist The Stata Listserver


[Date Prev][Date Next][Thread Prev][Thread Next][Date index][Thread index]

Re: st: mata: how function can return several results


From   wgould@stata.com (William Gould, Stata)
To   statalist@hsphsun2.harvard.edu
Subject   Re: st: mata: how function can return several results
Date   Tue, 17 Oct 2006 09:37:18 -0500

Abdelrahmen El Lahga writes, 

> I would like to write a subroutine in mata that can return several results
> ata once. More precisely if I define a function (myreg for exemple ) defined
> as
>
>       -------------start myreg
>       function myreg()
>       {
>               st_view(y, .,  st_local("yvar"))
>               st_view(x, ., st_local("xvar"))
>               bhat=invsym(x'*x)x'*y   // estimated coefficient
>               uhat=y-x*bhat       // residual 
>        }
>        ----------- finish myreg
>
>     how can i tell mata to return 2 results res1=bhat and res2=uhat? 
>
>     res1 and res2 are for use in the rest of my programme.  Ideally I want
>     some thing like this:
>
>        {b,u}=myreg() as can i code in gauss for exemple

There are two solutions to Abdelrahmen's problem:  (1) structures and 
(2) returning results in arguments.  I believe that (2) is the better 
solution in this case.

1.  The structure solution
--------------------------

I don't want to discuss this solution, but let me at least show it to you.

        structure regression_results {
                real colvector    bhat 
                real colvector    uhat
        }

        structure regression_results scalar myreg
        {
                structure regress_results scalar   res

                st_view(y, .,  st_local("yvar"))
                st_view(x, ., st_local("xvar"))
                res.bhat = invsym(x'*x)x'*y
                res.uhat = y-x*bhat
                return(res)
         }

This is a great solution but it requires a bit more setup (namely, the
definition of the structure).  It is merely because of that setup I wish to
suggest on an alternative solution.


2.  Returning resutls via arguments
-----------------------------------

Here is the solution that requires no setup:

         void regression_results(bhat, uhat)
         {
                st_view(y, .,  st_local("yvar"))
                st_view(x, ., st_local("xvar"))
                bhat = invsym(x'*x)x'*y
                uhat = y-x*bhat
         }

This program is very easy to use.   In a program, just code 

                regression_results(b, u)

and the predictions will be in b and the residuals in u.

Interactively, you must first define b and u before you can use them:

         : b = u = . 
         : regression_results(b, u)

We can mix input arguments and output arguments in the same function.
When I do that, I tend to put the output arguments last, but that is 
just a matter of style, and the opposite style (outputs first) is, to 
me, equally appealing.  Anyway, here is a better regression_results() 
in that it allows me to pass the names of yvar and xvar to the program.

         void regression_results(ynvarname, xvarname, bhat, uhat)
         {
                st_view(y, .,  st_local(yvarname))
                st_view(x, ., st_local(xvarname))
                bhat = invsym(x'*x)x'*y
                uhat = y-x*bhat
         }

If I were to include explicit declarations (again, it's a matter of style), 
here's how I would do that:

         void regression_results(string scalar ynvarname, 
                                 string scalar xvarname, 
                                 bhat, uhat)
         {
                real colvector   y, x

                st_view(y, .,  st_local(yvarname))
                st_view(x, ., st_local(xvarname))
                bhat = invsym(x'*x)x'*y
                uhat = y-x*bhat
         }

That is, when I include explicit declarations, it is my style to leave 
the output variables undeclared, which is the same as explicitly declaring
them to be "polymorphic matrix".  I don't care what type the output variables
are because I am going to replace them in this program and, by the time I'm
done, bhat and uhat will be real colvectors.

-- Bill
wgould@stata.com
*
*   For searches and help try:
*   http://www.stata.com/support/faqs/res/findit.html
*   http://www.stata.com/support/statalist/faq
*   http://www.ats.ucla.edu/stat/stata/



© Copyright 1996–2014 StataCorp LP   |   Terms of use   |   Privacy   |   Contact us   |   What's new   |   Site index