Announcement

Collapse
No announcement yet.
X
  • Filter
  • Time
  • Show
Clear All
new posts

  • Saving option within a program

    Dear All,

    I have the following rough code (it needs further amendements):

    Code:
    capture program drop marginteff
    program define marginteff, rclass
    version 10
    
    syntax varlist(min=3 max=3 numeric fv ts), grp(varlist min=1 max=1 numeric) [MIXed] [savedata(string) savegraph(string)]
    marksample touse
    
    tokenize `varlist'
    local var1="`1'" 
    local var2="`2'"
    local var12="`3'"
    
    tokenize `grp'
    local g="`1'"
    
    tempname B
    tempname xb
    tempvar rslope
    tempvar rint
    tempvar cross
    tempvar cross_se
    tempvar m_cross
    tempvar m_cross_se
    tempvar m_m_cross
    tempvar m_m_cross_se
    tempvar t_m_cross
    tempvar t_m_m_cross
    tempvar rslope
    tempvar rint
    tempvar prob
    
    mat `B' = e(b)
    mat score double `xb' = `B' if `touse'
    
    if "`mixed'"==""{
        qui predict `prob', pr
        qui predictnl `cross'=(_b[`var1']+_b[`var12'])*(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+_b[`var2']+_b[`var12']*`var1'))*(1-(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+_b[`var2']+_b[`var12']*`var1')))-_b[`var1']*(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'))*(1-(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'))) if `touse', se(`cross_se')
    }
    
    else if "`mixed'"!=""{
        qui predict `prob', mu
        qui predict `rslope' `rint' if `touse', reffect
        qui su `rslope' `rint'
        qui predictnl `cross'=(_b[`var1']+_b[`var12']+`rslope')*(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+_b[`var2']+(_b[`var12']+`rslope')*`var1'+`rint'))*(1-(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+_b[`var2']+(_b[`var12']+`rslope')*`var1'+`rint')))-(_b[`var1']+`rslope')*(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+`rslope'*`var1'+`rint'))*(1-(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+`rslope'*`var1'+`rint'))) if `touse', se(`cross_se')
    }
    
    bysort `g': egen `m_cross'=mean(`cross') if `touse'
    qui su `m_cross'
    label variable `m_cross' "(Avg) Interaction term"
    scalar `m_m_cross'=r(mean)
    bysort `g': egen `m_cross_se'=mean(`cross_se') if `touse'
    qui su `m_cross_se'
    label variable `m_cross_se' "(Avg) S.E."
    scalar `m_m_cross_se'=r(mean)
    gen `t_m_cross'=`m_cross'/`m_cross_se' if `touse'
    quietly su `t_m_cross'
    label variable `t_m_cross' "(Avg) T-statistic"
    scalar `t_m_m_cross'=r(mean)
    
    if "`savedata'"!=""{
        preserve 
        keep `m_cross' `m_cross_se' `t_m_cross'
        restore
    }  
    
    if "`savegraph'"!=""{
        preserve
        twoway(scatter `m_cross' `prob')
        "`savegraph'"
        restore
    }
    
    label variable `m_cross' "Cross effect"
    label variable `m_cross_se' "Standard Errors"
    label variable `t_m_cross' "t-test"
    
    su `m_cross' `m_cross_se' `t_m_cross'
    
    
    di
    di
    di "Significance test for cross term"
    di as text _dup(50) "-"
      di as text "     t-statistic  = " in  result %9.3f `m_m_cross'
      di as text "     s.e.         = " in  result %9.3f            `m_m_cross_se'
      di as text "     t-test       = " in  result %9.3f `t_m_m_cross'
      di as text "     P>|t|        = "   in  result %9.3f ttail(10000,`t_m_m_cross')
    di as text _dup(50) "-"
    end
    I included two options *savedata* and *savegraph*. After I run my analysis, I would like to save some data in a separate file and some graphs too. I would like to be able to include within savadata option the location for where I want to save the data (specifically, New_Analysis\Results). But I am not able to do so. Specifically, I would like to have something like:

    Code:
    marginteff y x1 x2 x12, mixed savedata(New_Analysis\Results\dataint.dta) savegraph(New_Analysis\Results\my_graph)
    How can I do that? Specifically, I cannot find the file dataint.dta in the directory I selected (there is no file dataint.dta at all on my pc). What's wrong with my code?

    A second issue I have is that before generating the summariy statistics of `m_cross' `m_cross_se' `t_m_cross' I try to label them. But it seems Stata cannot do that.

    Code:
     Variable |        Obs        Mean    Std. dev.       Min        Max
    -------------+---------------------------------------------------------
        __000007 |    186,443    .0121636    .0029053   .0055672   .0186525
        __000008 |    186,443    .0059492    .0016279   .0025022   .0092233
        __00000B |    186,443    2.106395    .3716783   .7090537   2.815147

    Thanks for your kind help.

    Dario
    Last edited by Dario Maimone Ansaldo Patti; 15 Nov 2021, 03:01.

  • #2
    If it can help in understanding my second problem above, I used set trace on. I noted the following:

    Code:
    - label variable `t_m_cross' "t-test"
    = label variable __00000B "t-test"
      --------------------------------------------------------------------------------------------- begin label ---
      - version 10.0
      - local vv : display "version " string(_caller()) ", missing:"
      - gettoken val : 0
      - if (strpos("`val'", "val") > 0 ) {
      = if (strpos("variable", "val") > 0 ) {
        gettoken val 0 : 0
        syntax anything [, nofix]
        if "`fix'" != "" {
        local fix ", nofix"
        }
        gettoken var rest : anything
        while `"`rest'"' != "" {
        gettoken lab rest : rest
        local label "`lab'"
        }
        local vlist : list anything - lab
        if "`lab'" == "." {
        local lab ""
        }
        foreach var of varlist `vlist' {
        `vv' _label `val' `var' `lab' `fix'
        }
        }
      - else {
      - `vv' _label `macval(0)'
      = version 14, missing: _label variable __00000B "t-test"
      - }
    I do not know why Stata cannot label the variable correctly.

    Dario

    Comment


    • #3
      The following example run in Stata 17.0 suggests that variable labels are ignored by the summarize command.
      Code:
      . set obs 100
      Number of observations (_N) was 0, now 100.
      
      . generate x = runiform()
      
      . label variable x "whatever"
      
      . describe x
      
      Variable      Storage   Display    Value
          name         type    format    label      Variable label
      ------------------------------------------------------------------------------------------------
      x               float   %9.0g                 whatever
      
      . summarize x
      
          Variable |        Obs        Mean    Std. dev.       Min        Max
      -------------+---------------------------------------------------------
                 x |        100    .4973389      .30869   .0030522   .9874847
      
      .
      and this continuation shows successful labeling of a temporary variable and use of the label by the tab command, suggesting the failure to use the labeling lies in summarize.
      Code:
      . tempvar t
      
      . generate `t' = runiform()
      
      . label variable `t' "whichever"
      
      . describe `t'
      
      Variable      Storage   Display    Value
          name         type    format    label      Variable label
      ------------------------------------------------------------------------------------------------
      __000000        float   %9.0g                 whichever
      
      . summarize `t'
      
          Variable |        Obs        Mean    Std. dev.       Min        Max
      -------------+---------------------------------------------------------
          __000000 |        100     .510208    .2838849   .0013631   .9944572
      
      . tab `t' in 1/5
      
        whichever |      Freq.     Percent        Cum.
      ------------+-----------------------------------
         .5948808 |          1       20.00       20.00
         .6701937 |          1       20.00       40.00
         .6880603 |          1       20.00       60.00
         .7970893 |          1       20.00       80.00
         .9794578 |          1       20.00      100.00
      ------------+-----------------------------------
            Total |          5      100.00
      With regard to savedata options, you never actually issue the command
      Code:
      save `"`savedata'"'
      to save the dataset, and note that in your example, the
      Code:
      New_Analysis\Results\
      directory will already need to exist as a subdirectory of your working directory.
      Last edited by William Lisowski; 15 Nov 2021, 08:52.

      Comment


      • #4
        William Lisowski thanks a lot for the clarifications. Regarding the first issue, you are totally right. I did not pass the command to save the file. Regarding the labelling issue, it is a bit annoying that summarize cannot accept a label of the variables. Maybe I can work the problem out in some way, maybe copying the variables into new temporary ones with the name I like and then use the sum command. Thanks a lot for your help.

        Comment


        • #5
          William Lisowski Thanks again for your help. I have another small issue. I changed the code to pass the save command. Specifically, I wrote:

          Code:
          **# Program to calculate marginal effects for the cross term
          
          capture program drop marginteff
          program define marginteff, rclass
          version 14
          
          syntax varlist(min=3 max=3 numeric fv ts), grp(varlist min=1 max=1 numeric) [MIXed] [savedata(string) savegraph(string)]
          marksample touse
          
          tokenize `varlist'
          local var1="`1'" 
          local var2="`2'"
          local var12="`3'"
          
          tokenize `grp'
          local g="`1'"
          
          tempname B 
          tempname xb
          tempvar rslope
          tempvar rint
          tempvar cross
          tempvar cross_se
          tempvar m_cross
          tempvar m_cross_se
          tempvar m_m_cross
          tempvar m_m_cross_se
          tempvar t_m_cross
          tempvar t_m_m_cross
          tempvar rslope
          tempvar rint
          tempvar prob
          tempvar N
          
          mat `B' = e(b)
          local j: colsof(`B')
          mat score double `xb' = `B' if `touse'
          local N=e(N)
          local df=`N'-`j'-1
          
          if "`mixed'"==""{
              qui predict `prob', pr
              qui predictnl `cross'=(_b[`var1']+_b[`var12'])*(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+_b[`var2']+_b[`var12']*`var1'))*(1-(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+_b[`var2']+_b[`var12']*`var1')))-_b[`var1']*(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'))*(1-(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'))) if `touse', se(`cross_se')
          }
          
          else if "`mixed'"!=""{
              qui predict `prob', mu
              qui predict `rslope' `rint' if `touse', reffect
              qui su `rslope' `rint'
              qui predictnl `cross'=(_b[`var1']+_b[`var12']+`rslope')*(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+_b[`var2']+(_b[`var12']+`rslope')*`var1'+`rint'))*(1-(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+_b[`var2']+(_b[`var12']+`rslope')*`var1'+`rint')))-(_b[`var1']+`rslope')*(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+`rslope'*`var1'+`rint'))*(1-(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+`rslope'*`var1'+`rint'))) if `touse', se(`cross_se')
          }
          
          bysort `g': egen `m_cross'=mean(`cross') if `touse'
          qui su `m_cross'
          label variable `m_cross' "(Avg) Interaction term"
          scalar `m_m_cross'=r(mean)
          bysort `g': egen `m_cross_se'=mean(`cross_se') if `touse'
          qui su `m_cross_se'
          label variable `m_cross_se' "(Avg) S.E."
          scalar `m_m_cross_se'=r(mean)
          gen `t_m_cross'=`m_cross'/`m_cross_se' if `touse'
          quietly su `t_m_cross'
          label variable `t_m_cross' "(Avg) T-statistic"
          scalar `t_m_m_cross'=r(mean)
          
          if "`savedata'"!=""{
              preserve 
              keep `m_cross' `m_cross_se' `t_m_cross'
              save `"`savedata'"'
              restore
          }  
          
          if "`savegraph'"!=""{
              preserve
              twoway(scatter `m_cross' `prob')
              save `"`savegraph'"'
              restore
          }
          
          tempname cross_effect
          tempname se
          tempname t_test
          
          gen `cross_effect'=`m_cross'
          gen `se'=`m_cross_se'
          gen `t_test'=`t_m_cross'
          
          su `cross_effect' `se' `t_test'
          
          di
          di
          di "Significance test for cross term"
          di as text _dup(50) "-"
            di as text "     t-statistic  = " in  result %9.3f `m_m_cross'
            di as text "     s.e.         = " in  result %9.3f            `m_m_cross_se'
            di as text "     t-test       = " in  result %9.3f `t_m_m_cross'
            di as text "     P>|t|        = "   in  result %9.3f ttail(`df',`t_m_m_cross')
          di as text _dup(50) "-"
          end
          I tried to add a replace option like the following:

          Code:
          save `"`savedata'"', replace
          or

          Code:
          save `"`savedata', replace"'
          or in the command window I typed

          Code:
          marginteff centeraf global centerafglob, grp(id) mixed savedata(New_Analysis\Results\mydata.dta, replace)
          However the file is saved with the extension .dta, replace and in any case, it does not me to replace the existing file. What is wrong with that way I am using?
          Regarding the second problem, I tried to generate new variables, but still sum does not display the correct name. I guess there is no any other trick I can use..

          Best

          Dario

          Comment


          • #6
            I did not read the details here but I wanted to point out that there is no such thing as the

            Code:
            ...marginal effects for the cross term
            in the sense that the product of two variables, say, x12=x1*x2, cannot change independently from those two variables, i. e., x1 and x2, that make up the product.

            Comment


            • #7
              Thanks for pointing this out daniel klein. I am aware of this. I am adapting to my needs the procedure suggested by Norton and Ai (2004). Here there is another paper, which shows an example using margins and the command inteff which produces basically the same results.

              Comment


              • #8
                William Lisowski I was able to solve the issue in #5. I changed from r(class) to e(class). Also I worked out to fix the name of the variables using summarize: I changed the code in the following way:

                Code:
                tempname cross_effect
                tempname se
                tempname t_test
                
                replace cross_effect=`m_cross'
                replace se=`m_cross_se'
                replace t_test=`t_m_cross'
                
                su cross_effect se t_test

                Comment


                • #9
                  Originally posted by Dario Maimone Ansaldo Patti View Post
                  William Lisowski Thanks again for your help. I have another small issue. I changed the code to pass the save command. Specifically, I wrote:

                  Code:
                  **# Program to calculate marginal effects for the cross term
                  
                  capture program drop marginteff
                  program define marginteff, rclass
                  version 14
                  
                  syntax varlist(min=3 max=3 numeric fv ts), grp(varlist min=1 max=1 numeric) [MIXed] [savedata(string) savegraph(string)]
                  marksample touse
                  
                  tokenize `varlist'
                  local var1="`1'"
                  local var2="`2'"
                  local var12="`3'"
                  
                  tokenize `grp'
                  local g="`1'"
                  
                  tempname B
                  tempname xb
                  tempvar rslope
                  tempvar rint
                  tempvar cross
                  tempvar cross_se
                  tempvar m_cross
                  tempvar m_cross_se
                  tempvar m_m_cross
                  tempvar m_m_cross_se
                  tempvar t_m_cross
                  tempvar t_m_m_cross
                  tempvar rslope
                  tempvar rint
                  tempvar prob
                  tempvar N
                  
                  mat `B' = e(b)
                  local j: colsof(`B')
                  mat score double `xb' = `B' if `touse'
                  local N=e(N)
                  local df=`N'-`j'-1
                  
                  if "`mixed'"==""{
                  qui predict `prob', pr
                  qui predictnl `cross'=(_b[`var1']+_b[`var12'])*(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+_b[`var2']+_b[`var12']*`var1'))*(1-(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+_b[`var2']+_b[`var12']*`var1')))-_b[`var1']*(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'))*(1-(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'))) if `touse', se(`cross_se')
                  }
                  
                  else if "`mixed'"!=""{
                  qui predict `prob', mu
                  qui predict `rslope' `rint' if `touse', reffect
                  qui su `rslope' `rint'
                  qui predictnl `cross'=(_b[`var1']+_b[`var12']+`rslope')*(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+_b[`var2']+(_b[`var12']+`rslope')*`var1'+`rint'))*(1-(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+_b[`var2']+(_b[`var12']+`rslope')*`var1'+`rint')))-(_b[`var1']+`rslope')*(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+`rslope'*`var1'+`rint'))*(1-(invlogit(`xb'-_b[`var2']*`var2'-_b[`var12']*`var12'+`rslope'*`var1'+`rint'))) if `touse', se(`cross_se')
                  }
                  
                  bysort `g': egen `m_cross'=mean(`cross') if `touse'
                  qui su `m_cross'
                  label variable `m_cross' "(Avg) Interaction term"
                  scalar `m_m_cross'=r(mean)
                  bysort `g': egen `m_cross_se'=mean(`cross_se') if `touse'
                  qui su `m_cross_se'
                  label variable `m_cross_se' "(Avg) S.E."
                  scalar `m_m_cross_se'=r(mean)
                  gen `t_m_cross'=`m_cross'/`m_cross_se' if `touse'
                  quietly su `t_m_cross'
                  label variable `t_m_cross' "(Avg) T-statistic"
                  scalar `t_m_m_cross'=r(mean)
                  
                  if "`savedata'"!=""{
                  preserve
                  keep `m_cross' `m_cross_se' `t_m_cross'
                  save `"`savedata'"'
                  restore
                  }
                  
                  if "`savegraph'"!=""{
                  preserve
                  twoway(scatter `m_cross' `prob')
                  save `"`savegraph'"'
                  restore
                  }
                  
                  tempname cross_effect
                  tempname se
                  tempname t_test
                  
                  gen `cross_effect'=`m_cross'
                  gen `se'=`m_cross_se'
                  gen `t_test'=`t_m_cross'
                  
                  su `cross_effect' `se' `t_test'
                  
                  di
                  di
                  di "Significance test for cross term"
                  di as text _dup(50) "-"
                  di as text " t-statistic = " in result %9.3f `m_m_cross'
                  di as text " s.e. = " in result %9.3f `m_m_cross_se'
                  di as text " t-test = " in result %9.3f `t_m_m_cross'
                  di as text " P>|t| = " in result %9.3f ttail(`df',`t_m_m_cross')
                  di as text _dup(50) "-"
                  end
                  I tried to add a replace option like the following:

                  Code:
                  save `"`savedata'"', replace
                  or

                  Code:
                  save `"`savedata', replace"'
                  or in the command window I typed

                  Code:
                  marginteff centeraf global centerafglob, grp(id) mixed savedata(New_Analysis\Results\mydata.dta, replace)
                  However the file is saved with the extension .dta, replace and in any case, it does not me to replace the existing file. What is wrong with that way I am using?
                  Regarding the second problem, I tried to generate new variables, but still sum does not display the correct name. I guess there is no any other trick I can use..

                  Best

                  Dario
                  Did you find a solution to the problem regarding the "replace" option?
                  Last edited by Matthew Smith Stata; 19 May 2022, 12:19.

                  Comment

                  Working...
                  X