Announcement

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

  • Marginsplot while setting a covariate to the age-specifc median?

    Hello, I was wondering if anyone knew how to specify margins for medians at specific ages? More precisly, I have a model that looks very similar to the model below. The one exception is that the model I actually use a mixed model. Unfortunately, I could not find a toy panel data that was similar to my own, but the dataset below pretty mudh has the variables that I will be using:


    Code:
    use http://fmwww.bc.edu/ec-p/data/wooldridge/cps78_85, clear
    recode educ (0/12=0) (13/18=1),gen(scol)
    reg lwage i.scol age c.age#c.age i.scol#c.age i.scol#c.age#c.age i.scol#c.exper

    In my dataset, exper is a time-varying variable that refers to years of work experience. I would like to predict the lwage values by scol across ages while holding exper at its age-specific median. So far, I did this:
    Code:
    quietly margins scol, at(c.age=(25(1)59) (median) c.exper)
    marginsplot

    However, I assume that is just setting ihs_faminc to the overall median rather than the age-specifc median.

    In simpler terms, if the median at age 30 is 8, I want to set exper at 8 years for age 30. If the median at age 31 is 10, I want to exper to 10 years for age 31. etc.

  • #2
    So what you are trying to do is have the values of age and exper march in parallel in your -at()- conditions. You can't do that with a single -at()- specification, nor, within -at()- can you ask for -(median) exper- to condition itself on the current value of age. So you have to build this up piece by piece, with a separate -at()- specification for each age. Like this:
    Code:
    local ats
    forvalues a = 25/59 {
        centile exper if age == `a'
        local ats `ats' at(age = `a' exper = `r(c_1)')
    }
    
    margins scol, `ats'
    marginsplot
    Now, in the cps78_85 example data, the number of people at age age is pretty small, and when split further by the values of scol you are taking medians of tiny numbers of observations, and they are, as a result, pretty noisy. I trust that in your actual data set you have ample numbers of people at all ages to support this kind of analysis.

    Comment


    • #3
      Hi Clyde, thanks so much for your reply! When I run the code, my x-axis is 0 and 1 (i.e., scol) rather than age. Essentially, I would like two estimated trends: one for scol == 0 and one for scol == 1. Is there a way to correct this? At the moment, it seems that age is being treated as a categorical variable

      And yes, I am using a much larger household panel study.

      Comment


      • #4
        Well, this makes it a little more complicated. The simple expedient of -xdimension(age)- on your -marginsplot- command will not work because given the multiple -at()-'s needed, Stata will tell you that age is not a dimension in your -margins- output. So, you have to save the -margins- results in a file, then -use- that file and create the graph using -twoway line- and -twoway rcap-.

        It will go something like this:
        Code:
        local ats
        forvalues a = 25/59 {
            centile exper if age == `a'
            local ats `ats' at(age = `a' exper = `r(c_1)')
        }
        
        tempfile for_graph
        margins scol, `ats' saving(`for_graph')
        
        frame create for_graph
        frame change for_graph
        use `for_graph'
        rename _m1 scol
        rename _at2 age
        keep _margin _ci* scol age
        reshape wide _margin _ci*, i(age) j(scol)
        graph twoway (line _margin* age) (rcap _ci_lb0 _ci_ub0 age) (rcap _ci_lb1 _ci_ub1 age)
        Caution: I cannot promise you that _m1 will be the variable with scol and _at2 will be the one with age. Once you read in that data set with the -margins- output, you will have to examine it to see which variables are named what. I can promise you that _margin and _ci* will be correct, but the naming of everything else is hard to predict.

        Comment


        • #5
          If your real-data model is like the working example, where scol, age, and exper are the only predictors in the model, then you can use option over() with statistic median and an if condition to produce your graph.

          Here it is in action using the above working example.
          Code:
          use http://fmwww.bc.edu/ec-p/data/wooldridge/cps78_85, clear
          recode educ (0/12=0) (13/18=1),gen(scol)
          reg lwage i.scol age c.age#c.age i.scol#c.age i.scol#c.age#c.age i.scol#c.exper
          
          margins scol if inrange(age,25,59), over(age) at((median) c.exper)
          marginsplot, xdim(age)
          Notice (if you run this example) that the margins header reports the median exper value at each level of age (in the restricted range).

          Here is the resulting graph.

          Click image for larger version

Name:	plot.png
Views:	1
Size:	110.4 KB
ID:	1744375

          Comment


          • #6
            Amazing! Thank you both so much, Clyde and Jeff!

            Comment

            Working...
            X