📄 canon.ado
字号:
via cov = V^(1/2) corr V^(1/2)
Then we calculate the loadings via
rholoadA = A*cov*V^(-1/2) in book speak or
canloadA = coefA'*SDAi*A*SDAi*SDA here.
= coefA'*SDAI*A
*/
matrix `SDAi' = syminv(`SDA')
matrix `SDCi' = syminv(`SDC')
matrix `canloadA' = `coefA''*`SDAi'*`A'
matrix `canloadC' = `coefC''*`SDCi'*`C'
matrix `canloadM' = `coefA''*`SDAi'*`B'
matrix `canloadM2' = `coefC''*`SDCi'*`B''
eret post `T' `bigABC', dof(`nobs1') esample(`touse')
if _caller()<6 {
mat S_E_ccor = `ccor'
}
eret matrix corr_mixed = `corr_mixed'
eret matrix corr_var2 = `corr_dep'
eret matrix corr_var1 = `corr_ind'
eret matrix ccorr `ccor'
mat rownames `TC' = ":1"
* eret matrix bstdcoef `TC'
/* put correct column labels on
these matrices and save them out. */
local colnam : colnames `coefC'
if `"`lc'"' =="" {
local wc : word count `colnam'
local ncn ":1"
forv i=2/`wc' {
local ncn "`ncn' :`i'"
}
matrix colnames `coefC' = `ncn'
matrix colnames `coefA' = `ncn'
matrix colnames `stdcoefC' = `ncn'
matrix colnames `stdcoefA' = `ncn'
}
else {
matrix colnames `coefC' = ":`lc'"
matrix colnames `coefA' = ":`lc'"
matrix colnames `stdcoefA' = ":`lc'"
matrix colnames `stdcoefC' = ":`lc'"
}
eret matrix stdcoef_var2 = `stdcoefA', copy
eret matrix stdcoef_var1 = `stdcoefC', copy
eret matrix rawcoef_var2 = `coefA',copy
eret matrix rawcoef_var1 = `coefC',copy
/* put correct row labels on these matrices and
save them out */
if `"`lc'"' == "" {
mat rownames `canloadC' = `ncn'
mat rownames `canloadA' = `ncn'
mat rownames `canloadM' = `ncn'
mat rownames `canloadM2' = `ncn'
}
else {
mat rownames `canloadC' = ":`lc'"
mat rownames `canloadA' = ":`lc'"
mat rownames `canloadM' = ":`lc'"
mat rownames `canloadM2' = ":`lc'"
}
/* I'd like these all transposed
before putting them out, so let's do that... */
mat `canloadC' = `canloadC''
mat `canloadA' = `canloadA''
mat `canloadM' = `canloadM''
mat `canloadM2' = `canloadM2''
eret matrix canload21 `canloadM2'
eret matrix canload12 `canloadM'
eret matrix canload22 `canloadA'
eret matrix canload11 `canloadC'
/* double save in S_E_<stuff> and e() */
eret scalar N = `nobs'
eret scalar df = `nobs1'
eret scalar n_cc = `ncc'
if "`lc'" != "" {
eret scalar n_lc = `lc'
eret scalar n_cc = 1
}
if `"`first'"' != "" {
eret scalar n_cc = `first'
}
global S_E_nobs `e(N)'
global S_E_tdf `e(df)'
global S_E_lc `e(n_lc)'
eret local estat_cmd "canon_estat"
eret local predict "canon_p"
eret local cmd "canon"
eret local wtype "`weight'"
eret local wexp "`exp'"
global S_E_cmd "canon"
GetTests `p' `q' `nobs'
MoreTests `p' `q' `nobs'
}
else {
if `"`e(cmd)'"'!="canon" {
error 301
}
if _by() {
error 190
}
syntax [, `options' ]
if `"`stdcoef'"'!="" & `"`coefmatrix'"'!="" {
di as err "cannot specify stdcoef and coefmatrix " ///
"options together"
error(198)
}
if `"`stdcoef'"'=="" & `"`coefmatrix'"'=="" & `"`format'"' != "" {
di as err "format() may only be specified with stdcoef or coefmatrix"
exit(198)
}
if "`format'" =="" {
local format format(%8.4f)
}
else {
quietly di `format' 0
local format format(`format')
}
if "`notests'"!="" & "`tests'"!="" {
di as err "test and notests may not be specified together"
exit 198
}
di
local lcs = e(n_cc)
}
/* Display output now that calculations are done */
local lcl 76 /* line length */
if `"`stdcoef'"' != "" {
di _n in gr "Canonical correlation analysis " _col(56) ///
"Number of obs =" in ye %8.0f e(N)
di _n in gr "Standardized coefficients for the first variable set"
matlist e(stdcoef_var1), left(4) `format' border(bottom)
di
di _n in gr "Standardized coefficients for the second variable set"
matlist e(stdcoef_var2), left(4) `format' border(bottom)
di
di in smcl in gr "{hline `lcl'}"
}
else if `"`coefmatrix'"' != "" {
di _n in gr "Canonical correlation analysis " _col(56) ///
"Number of obs =" in ye %8.0f e(N)
di _n in gr "Raw coefficients for the first variable set"
matlist e(rawcoef_var1), left(4) `format' border(bottom)
di _n in gr "Raw coefficients for the second variable set"
matlist e(rawcoef_var2), left(4) `format' border(bottom)
di
di in smcl in gr "{hline `lcl'}"
}
else {
if "`lc'"!="" {
di _n in gr "Linear combinations for canonical " ///
"correlation " `lc' _col(56) "Number of obs =" ///
in ye %8.0f e(N)
}
else {
di _n in gr "Linear combinations for canonical " ///
"correlations " _col(56) "Number of obs =" ///
in ye %8.0f e(N)
}
eret di, level(`level')
di in gr _col(38) "(Standard errors estimated conditionally)"
}
di in gr "Canonical correlations:"
mat list e(ccorr), nohead nonames noblank format(%9.4f)
if "`notests'"=="" {
di
di in gr in smcl "{hline `lcl'}"
di in gr "Tests of significance of all canonical correlations"
tempname tmat
mat define `tmat' = e(stat_m)
di
DisplayTest `tmat'
foreach num of local tests {
di in smcl in green "{hline `lcl'}"
if `num' < `lcs' {
di in gr "Test of significance of canonical correlations `num'-`lcs'"
}
else {
if `num' == `lcs' {
di in gr "Test of significance of canonical correlation `lcs'"
}
}
if `num' <= `lcs' {
di
mat define `tmat' = e(stat_`num')
mat rownames `tmat' = Wilks
DisplayTest `tmat'
}
else {
/* SHOULD NOT GET HERE */
di in gr "Cannot display tests for nonexistent canonical correlation `num'."
}
}
di in smcl in green "{hline `lcl'}"
di in smcl in gr "{ralign `lcl':e = exact, a = approximate, u = upper bound on F}"
}
end
/* Tests of subsequent canonical correlations after the first. */
program define MoreTests, eclass
version 8.1
local p `1'
local q `2'
local n `3'
tempname ccorr
mat `ccorr' = e(ccorr)
local ncc = colsof(`ccorr')
tempname df1 df2 w t wilks wilksF fu testm
scalar `wilks' = 1
forvalues i = 1/`ncc' {
scalar `wilks' = `wilks'*(1-`ccorr'[1,`i']^2)
}
forvalues i = 1/`ncc' {
local pn `p' - `i' + 1
local qn `q' - `i' + 1
scalar `df1' = (`pn')*(`qn')
scalar `w' = `n' - (`p' + `q' + 3)/2.0
if `pn'*`qn' == 2 {
scalar `t' = 1
}
else{
scalar `t' = sqrt(((`pn')^2 *(`qn')^2 -4)/ ///
((`pn')^2 + (`qn')^2 - 5))
}
if `ncc' - `i' + 1 <= 2 {
local wEx = 1
}
else {
local wEx = 0
}
scalar `df2' = `w'*`t' - .5*((`pn')*(`qn')) + 1
if `i' > 1 {
scalar `wilks' = `wilks'/(1-`ccorr'[1,`i'-1]^2)
}
scalar `fu' = (`wilks')^(1/`t')
scalar `wilksF' = ((1-`fu')/`fu')*(`df2'/`df1')
mat `testm' = (`wilks', `df1', ///
`df2', `wilksF', fprob(`df1', `df2', `wilksF'), `wEx')
mat colnames `testm' = statistic df1 df2 F pvalue exact
mat rownames `testm' = Wilks
ereturn matrix stat_`i' = `testm'
}
end
/* Notes: s = min(p,q) = ncc = colsof(`ccorr')
m = 1/2(max - s - 1)
N = 1/2(n - q - p - 2) = 1/2(n - max - ncc - 2)
see p. 368 Rencher, A. _Methods of Multivariate Analysis_ 2nd Ed.
These relationships are used to calculate many of the df's for
the various statistics
*/
program define GetTests, eclass
version 8.0
local p `1'
local q `2'
local n `3'
local max = max(`p', `q')
tempname df1 df2 w t ccorr wilks wilksF fo pillai pillaiF
tempname lawley lawleyF roy royF dfp1 dfp2 dfl2 dfr1 dfr2
scalar `df1' = `p'*`q'
scalar `w' = `n' - (`p' + `q' + 3)/2.0
scalar `t' = sqrt(((`p')^2*(`q')^2 - 4)/((`p')^2 + (`q')^2 -5))
if (`p'*`q' == 2) scalar `t' = 1
scalar `df2' = `w'*`t'- .5*`p'*`q' + 1.0
ereturn scalar df1 = `df1'
ereturn scalar df2 = `df2'
mat `ccorr' = e(ccorr)
local ncc = colsof(`ccorr')
if `ncc' <= 2 {
local wEx = 1
}
else {
local wEx = 0
}
if `ncc' == 1 {
local rEx = 1
}
else {
local rEx = 0
}
scalar `wilks' = 1
scalar `pillai' = 0
scalar `lawley' = 0
scalar `roy' = `ccorr'[1,1]^2
scalar `roy' = `roy'/(1-`roy')
forvalues i = 1/`ncc' {
scalar `fo' = `ccorr'[1,`i']^2
scalar `wilks' = `wilks'*(1-`fo')
scalar `pillai' = `pillai' + `fo'
scalar `lawley' = `lawley' + `fo'/(1-`fo')
}
scalar `fo' = (`wilks')^(1/`t')
scalar `wilksF' = ((1-`fo')/`fo')*(`df2'/`df1')
scalar `pillaiF' = `pillai'/`ncc'
scalar `dfp1' = `max'*`ncc'
scalar `dfp2' = (`n' - `max' - 1)*`ncc'
if ((`dfp1' == `df1') & (`dfp2' == `df2')) {
local pEx = 1
}
else {
local pEx = 0
}
scalar `pillaiF' = (`pillaiF'*`dfp2')/(`dfp1'*(1 - `pillaiF'))
scalar `dfl2' = `ncc'*(`n'-`max'-`ncc' -2) + 2
scalar `lawleyF' = `lawley'*`dfl2'/(`ncc'*`dfp1')
if ((`dfp1' == `df1') & (`dfl2' == `df2')) {
local lEx = 1
}
else {
local lEx = 0
}
scalar `dfr1' = `max'
scalar `dfr2' = `n' - `max' - 1
scalar `royF' = `roy'*`dfr2'/(`dfr1')
tempname testmat
matrix `testmat' = (`wilks', `df1', `df2', `wilksF', ///
fprob(`df1',`df2', `wilksF'), `wEx' \ ///
`pillai', `dfp1', `dfp2', `pillaiF', ///
fprob(`dfp1',`dfp2',`pillaiF'), `pEx' \ ///
`lawley', `dfp1', `dfl2', `lawleyF', ///
fprob(`dfp1', `dfl2', `lawleyF'), `lEx' \ ///
`roy',`dfr1',`dfr2', `royF', ///
fprob(`dfr1', `dfr2', `royF'), `rEx')
mat colnames `testmat' = statistic df1 df2 F pvalue exact
mat rownames `testmat' = Wilks Pillai Lawley Roy
ereturn matrix stat_m = `testmat'
end
program define GetEq, sclass
sret clear
gettoken open 0 : 0, parse("(")
if `"`open'"' != "(" {
error 198
}
gettoken next 0 : 0, parse(")")
while `"`next'"' != ")" {
if `"`next'"'=="" {
error 198
}
local list `list'`next'
gettoken next 0 : 0, parse(")")
}
sret local rest `"`0'"'
tokenize `list', parse(" :")
if "`2'"==":" {
sret local name "`1'"
mac shift 2
}
local 0 `*'
syntax varlist
sret local varlist "`varlist'"
end
program DisplayTest
version 8.0
args mat
tempname tm
local fo = rowsof(`mat')
di in green in smcl "{col 26}Statistic {col 41}df1" ///
"{col 50}df2 {col 65}F {col 71}Prob>F"
forvalues i = 1/`fo' {
matrix `tm' = `mat'[`i', 1...]
local test : rownames `tm'
if "`test'" == "Wilks" local test "Wilks' lambda"
if "`test'" == "Pillai" local test "Pillai's trace"
if "`test'" == "Lawley" local test "Lawley-Hotelling trace"
if "`test'" == "Roy" local test "Roy's largest root"
if `mat'[`i',6] == 1 {
local ex e /* exact */
}
else {
if substr("`test'",1,1)!="R" {
local ex a /* approximate */
}
else {
local ex u /* Roy's is upper bound */
}
}
di in green %23s "`test' " ///
in yellow %11.6g `mat'[`i',1] " " %8.0g `mat'[`i',2] ///
" " %8.0g `mat'[`i',3] " " %12.4f `mat'[`i',4] ///
" " %10.4f `mat'[`i',5] %2s "`ex'"
}
end
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -