*! version 2.0.4 JMGarrett 14May98 STB-43 sg33.1 /* Program to calculate adjusted probabilities for nominal variables */ /* Form: adjprop y, by(x1 x2) adj(cov1 cov2 ...) options */ /* Options required: by (x1 [x2]) <-- nominal variables only */ /* Options allowed: adjust, model, level, graph, bar, graph_options */ program define adjprop version 4.0 #delimit ; local options "BY(string) Adjust(string) Model Graph L2title(string) L1title(string) T2title(string) Bar Level(real 95) *" ; #delimit cr local varlist "req ex min(1) max(1)" local if "opt" parse "`*'" parse "`varlist'", parse(" ") preserve capture keep `if' local yvar="`1'" quietly drop if `yvar'==. * If there are covariates, drop missing values, calculate means parse "`adjust'", parse(" ") local numcov=0 local i=1 while "`1'"~="" { local equal=index("`1'","=") if `equal'==0 { local cov`i'="`1'" local mcov`i'="mean" } if `equal'~=0 { local cov`i'=substr("`1'",1,`equal'-1) local mcov`i'=substr("`1'",`equal'+1,length("`1'")) } quietly drop if `cov`i''==. local covlist `covlist' `cov`i'' local covdisp `covdisp' `1' local i=`i'+1 macro shift local numcov=`i'-1 } local i=1 while `i'<=`numcov' { if "`mcov`i''"=="mean" { quietly sum `cov`i'' local mcov`i'=_result(3) } local i=`i'+1 } keep `yvar' `by' `covlist' * Read in X variables and create dummy variables parse "`by'", parse(" ") local xvar1="`1'" local vlblx1 : variable label `xvar1' quietly drop if `xvar1'==. quietly tab `xvar1', gen(X) local numcat1=_result(2) local i=2 while `i'<=`numcat1' { local xlist1 `xlist1' X`i' local i=`i'+1 } macro shift if "`1'"=="" { local x2=0 local numcat=`numcat1' } if "`1'"~="" { local xlist1 "" local i=2 while `i'<=`numcat1' { rename X`i' X1`i' local xlist1 `xlist1' X1`i' local i=`i'+1 } local x2=1 local xvar2="`1'" quietly drop if `xvar2'==. local vlblx2 : variable label `xvar2' quietly tab `xvar2', gen(X2) local numcat2=_result(2) local i=2 while `i'<=`numcat2' { local xlist2 `xlist2' X2`i' local i=`i'+1 } local numcat=`numcat1'*`numcat2' macro shift if "`1'"~="" { disp in red "Only two X variables allowed in the by( ) option" exit } * create interaction terms local i=2 while `i'<=`numcat1' { local j=2 while `j'<=`numcat2' { quietly gen I`i'`j'=X1`i'*X2`j' local intlist `intlist' I`i'`j' local j=`j'+1 } local i=`i'+1 } } * Run logistic regression to get parameter estimates if "`model'"~="model" { quietly logistic `yvar' `xlist1' `xlist2' `intlist' `covlist' } if "`model'"=="model" { logistic `yvar' `xlist1' `xlist2' `intlist' `covlist' } local varlbly : variable label $S_E_depv estimates hold logest * LR test for overall association, and interaction if present local l1=-2*_result(2) quietly logistic `yvar' `covlist' local l2=-2*_result(2) local df=`numcat'-1 local chisq=`l2'-`l1' local probchi=chiprob(`df',`chisq') if `x2'==1 { quietly logistic `yvar' `xlist1' `xlist2' `covlist' local l2=-2*_result(2) local dfi=(`numcat1'-1)*(`numcat2'-1) local chisqi=`l2'-`l1' local pchisqi=chiprob(`dfi', `chisqi') } estimates unhold logest * Collapse to 1 obs. per category, dummy variables, and covariates tempvar count quietly gen `count'=1 sort `by' #delimit ; collapse `count' `yvar' `xlist1' `xlist2' `intlist', by(`by') max(. `yvar' `xlist1' `xlist2' `intlist') sum(numobs) ; #delimit cr quietly replace $S_E_depv=. * Replace covariates with their means (or specified values) local i=1 while `i'<=`numcov' { quietly gen `cov`i''=`mcov`i'' local i=`i'+1 } * Calculate the adjusted probabilities (risks) and confidence intervals tempvar linpred predict adjprob predict se, stdp predict `linpred', xb local z=invnorm((1-`level'/100)/2) gen upper=1/(1+exp(-`linpred'+`z'*se)) gen lower=1/(1+exp(-`linpred'-`z'*se)) * Print results display " " if `numcov'>0 { #delimit ; display in yel "*" in green "Adjusted" in yel "*" in green " Probabilities and `level'% Confidence Intervals" ; #delimit cr local probtyp="adjprob" } if `numcov'==0 { #delimit ; display in yel "*" in green "Unadjusted" in yel "*" in green " Probabilities and `level'% Confidence Intervals"; #delimit cr local probtyp="prob" quietly gen prob=adjprob } display " " display in gr " Outcome:" in yel " `varlbly' -- $S_E_depv" if `x2'==0 { display in gr " Nominal X:" in yel " `vlblx1' -- `xvar1'" } if `x2'==1 { display in gr " Nominal X1:" in yel " `vlblx1' -- `xvar1'" display in gr " Nominal X2:" in yel " `vlblx2' -- `xvar2'" display in gr " Interaction:" in yel " `xvar1' * `xvar2'" } if `numcov'~=0 {display in gr " Covariates:" in yel " `covdisp'"} if `numcov'==0 {display in gr " Covariates:" in yel " (none)"} list `by' numobs `probtyp' se lower upper, noob nod disp " " disp in gr " Likelihood ratio test for difference of `numcat' probabilities:" disp " " disp in green " LR Chi2(`df') = " in yellow %6.2f `chisq' if `probchi'>=.0001 { disp in green " Prob > Chi2 = " in yellow %7.4f `probchi' } if `probchi'<.0001 { disp in green " Prob > Chi2 < " in yellow "0.0001" } if `x2'==1 { disp " " #delimit ; disp in gr " Likelihood ratio test of interaction for" in yellow " `xvar1' * `xvar2'" in green ":"; #delimit cr disp " " disp in green " LR Chi2(`dfi') = " in yellow %6.2f `chisqi' if `pchisqi'>=.0001 { disp in green " Prob > Chi2 = " in yellow %7.4f `pchisqi' } if `pchisqi'<.0001 { disp in green " Prob > Chi2 < " in yellow "0.0001" } } * Graph the results, if requested if "`graph'"=="graph" { more if "`l2title'"=="" {local l2title "`varlbly' -- $S_E_depv"} if "`l1title'"=="" & `numcov'==0 { if "`bar'"=="" { local l1title "Unadjusted Probabilities and `level'% CI" } if "`bar'"=="bar" { local l1title "Unadjusted Probabilities" } } if "`l1title'"=="" & `numcov'>0 { if "`bar'"=="" { local l1title "Adjusted Probabilities and `level'% CI" } if "`bar'"=="bar" { local l1title "Adjusted Probabilities" } } if `x2'==0 { if "`bar'"=="" { #delimit ; graph adjprob lower upper `xvar1', c(.II) s(Oii) `options' l2("`l2title'") l1("`l1title'") ; #delimit cr } if "`bar'"=="bar" { if "`t2title'"=="" & "`vlblx1'"=="" {local t2title "`xvar1'"} if "`t2title'"=="" & "`vlblx1'"~="" { local t2title "`vlblx1' -- `xvar1'" } sort `xvar1' #delimit ; graph adjprob, by(`xvar1') bar `options' l2("`l2title'") l1("`l1title'") t2("`t2title'") ; #delimit cr } } if `x2'==1 { local x2val : value label `xvar2' sort `xvar2' `xvar1' local i=1 local n=1 while `n'<=_N { if `xvar2'[`n']~=`xvar2'[`n'-1] { local catv`i'=`xvar2'[`n'] local catv `catv' `catv`i'' local i=`i'+1 } local n=`n'+1 } if "`x2val'"~="" { local i=1 while `i'<=`numcat2' { local x2lbl`i' : label `x2val' `catv`i'' local i=`i'+1 } } rename adjprob _M reshape groups `xvar2' `catv' reshape vars _M reshape con `xvar1' reshape wide local i=1 while `i'<=`numcat2' { if "`x2val'"~="" {label var _M`catv`i'' "`xvar2' = `x2lbl`i''"} else {label var _M`catv`i'' "`xvar2' = `catv`i''"} local i=`i'+1 } if "`bar'"=="bar" { if "`l1title'"=="" & `numcov'==0 { local l1title "Unadjusted Probabilities" } if "`l1title'"=="" & `numcov'>0 { local l1title "Adjusted Probabilities" } sort `xvar1' graph _M*, by(`xvar1') bar `options' l2("`l2title'") l1("`l1title'") } if "`bar'"~="bar" { graph _M* `xvar1', `options' l2("`l2title'") l1("`l1title'") } } } end