我在特定功能fda
中使用包fRegress
。此函数包含另一个名为eigchk
的函数,用于检查系数矩阵是否为单数。
这是包装所有者(J. O. Ramsay,Giles Hooker和Spencer Graves)写的功能。
eigchk <- function(Cmat) {
# check Cmat for singularity
eigval <- eigen(Cmat)$values
ncoef <- length(eigval)
if (eigval[ncoef] < 0) {
neig <- min(length(eigval),10)
cat("\nSmallest eigenvalues:\n")
print(eigval[(ncoef-neig+1):ncoef])
cat("\nLargest eigenvalues:\n")
print(eigval[1:neig])
stop("Negative eigenvalue of coefficient matrix.")
}
if (eigval[ncoef] == 0) stop("Zero eigenvalue of coefficient matrix.")
logcondition <- log10(eigval[1]) - log10(eigval[ncoef])
if (logcondition > 12) {
warning("Near singularity in coefficient matrix.")
cat(paste("\nLog10 Eigenvalues range from\n",
log10(eigval[ncoef])," to ",log10(eigval[1]),"\n"))
}
}
正如你可以看到的那样,如果条件检查logcondition
是否大于12,则打印出特征值的范围。
以下代码实现了粗糙度正则化的使用。该代码取自本书&#34;使用R和Matlab进行功能数据分析&#34;。
annualprec = log10(apply(daily$precav,2,sum))
tempbasis =create.fourier.basis(c(0,365),65)
tempSmooth=smooth.basis(day.5,daily$tempav,tempbasis)
tempfd =tempSmooth$fd
templist = vector("list",2)
templist[[1]] = rep(1,35)
templist[[2]] = tempfd
conbasis = create.constant.basis(c(0,365))
betalist = vector("list",2)
betalist[[1]] = conbasis
SSE = sum((annualprec - mean(annualprec))^2)
Lcoef = c(0,(2*pi/365)^2,0)
harmaccelLfd = vec2Lfd(Lcoef, c(0,365))
betabasis = create.fourier.basis(c(0, 365), 35)
lambda = 10^12.5
betafdPar = fdPar(betabasis, harmaccelLfd, lambda)
betalist[[2]] = betafdPar
annPrecTemp = fRegress(annualprec, templist, betalist)
betaestlist2 = annPrecTemp$betaestlist
annualprechat2 = annPrecTemp$yhatfdobj
SSE1.2 = sum((annualprec-annualprechat2)^2)
RSQ2 = (SSE - SSE1.2)/SSE
Fratio2 = ((SSE-SSE1.2)/3.7)/(SSE1/30.3)
resid = annualprec - annualprechat2
SigmaE. = sum(resid^2)/(35-annPrecTemp$df)
SigmaE = SigmaE.*diag(rep(1,35))
y2cMap = tempSmooth$y2cMap
stderrList = fRegress.stderr(annPrecTemp, y2cMap, SigmaE)
betafdPar = betaestlist2[[2]]
betafd = betafdPar$fd
betastderrList = stderrList$betastderrlist
betastderrfd = betastderrList[[2]]
作为惩罚因素,作者使用某些lambda
。
以下代码实现了对相应`lambda。
loglam = seq(5,15,0.5)
nlam = length(loglam)
SSE.CV = matrix(0,nlam,1)
for (ilam in 1:nlam) {
lambda = 10ˆloglam[ilam]
betalisti = betalist
betafdPar2 = betalisti[[2]]
betafdPar2$lambda = lambda
betalisti[[2]] = betafdPar2
fRegi = fRegress.CV(annualprec, templist,
betalisti)
SSE.CV[ilam] = fRegi$SSE.CV
}
通过更改loglam
和交叉验证的值,我认为等于最佳lambda
,但如果loglam
的长度为大或其值导致系数矩阵要善意。我收到以下消息:
Log10 Eigenvalues range from
-5.44495317739048 to 6.78194912518214
由上面已经提到的函数eigchk
创建。
现在我的问题是,有没有办法赶上这个所谓的警告?通过catch我的意思是一些功能或方法在发生这种情况时发出警告我可以调整loglam
的值。由于在此消息打印旁边的函数中没有实际的警告定义,我的想法已经用尽了。
非常感谢你的建议。
答案 0 :(得分:0)
通过&#34;抓住警告&#34;,如果您的意思是,会提醒您loglam
存在潜在问题,那么您可能需要查看try
和{{ 1}}功能。然后,如果满足任何警告条件,您可以定义要实现的行为。
如果您只想存储警告的输出(可能从问题标题中假设,但可能不是您想要的),请尝试查看tryCatch
。