-
Notifications
You must be signed in to change notification settings - Fork 9
/
Copy patheval.fd.R
217 lines (174 loc) · 6.3 KB
/
eval.fd.R
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
predict.fdSmooth <- function(object, newdata=NULL, Lfdobj=0,
returnMatrix=FALSE, ...){
if(is.null(newdata)){
newdata <- object$argvals
}
eval.fd(newdata, object$fd, Lfdobj, returnMatrix=returnMatrix)
}
fitted.fdSmooth <- function(object, returnMatrix=FALSE, ...){
newdata <- object$argvals
eval.fd(newdata, object$fd, 0, returnMatrix=returnMatrix)
}
residuals.fdSmooth <- function(object, returnMatrix=FALSE, ...){
newdata <- object$argvals
pred <- eval.fd(newdata, object$fd, 0, returnMatrix=returnMatrix)
object$y-pred
}
predict.fdPar <- function(object, newdata=NULL, Lfdobj=0,
returnMatrix=FALSE, ...){
predict.fd(object$fd, newdata, Lfdobj,
returnMatrix=returnMatrix, ...)
}
predict.fd <- function(object, newdata=NULL, Lfdobj=0,
returnMatrix=FALSE, ...){
if(is.null(newdata)){
basis <- object$basis
type <- basis$type
if(length(type) != 1)
stop('length(object$type) must be 1; is ',
length(type) )
newdata <- {
if(type=='bspline')
unique(knots(basis, interior=FALSE))
else basis$rangeval
}
}
eval.fd(newdata, object, Lfdobj, returnMatrix=returnMatrix)
}
# ----------------------------------------------------------------------------
eval.fd <- function(evalarg, fdobj, Lfdobj=0, returnMatrix=FALSE) {
# EVAL_FD evaluates a functional data observation at argument
# values EVALARG.
#
# LFDOBJ is a functional data object defining the order m
# HOMOGENEOUS linear differential operator of the form
# Lx(t) = w_0(t) x(t) + ... + w_{m-1}(t) D^{m-1}x(t) +
# \exp[w_m(t)] D^m x(t)
#
# Arguments:
# EVALARG ... A vector of values at which all functions are to
# evaluated.
# FDOBJ ... Functional data object
# LFDOBJ ... A linear differential operator object
# applied to the functions before they are evaluated.
# RETURNMATRIX ... If False, a matrix in sparse storage model can be returned
# from a call to function BsplineS. See this function for
# enabling this option.
# Note that the first two arguments may be interchanged.
# Returns: An array of function values corresponding to the evaluation
# arguments in EVALARG
# Last modified Oct 19, 2012 by Spencer Graves
# Check LFDOBJ
Lfdobj <- int2Lfd(Lfdobj)
# Exchange the first two arguments if the first is an FD object
# and the second numeric
if (inherits(fdobj, "numeric") && inherits(evalarg, "fd")) {
temp <- fdobj
fdobj <- evalarg
evalarg <- temp
}
# check EVALARG
# if (!(is.numeric(evalarg))) stop("Argument EVALARG is not numeric.")
Evalarg <- evalarg
if(!is.numeric(evalarg)){
op <- options(warn=-1)
evalarg <- as.numeric(Evalarg)
options(op)
nNA <- sum(is.na(evalarg))
if(nNA>0)
stop('as.numeric(evalarg) contains ', nNA,
' NA', c('', 's')[1+(nNA>1)],
'; class(evalarg) = ', class(Evalarg))
}
evaldim <- dim(evalarg)
if (!(length(evaldim) < 3))
stop("Argument 'evalarg' is not a vector or a matrix.")
# check FDOBJ
# if (!(inherits(fdobj, "fd")))
# stop("Argument FD is not a functional data object.")
# Extract information about the basis
basisobj <- fdobj$basis
nbasis <- basisobj$nbasis
rangeval <- basisobj$rangeval
onerow <- rep(1,nbasis)
temp <- c(evalarg)
temp <- temp[!(is.na(temp))]
EPS <- 5*.Machine$double.eps
if (min(temp) < rangeval[1]-EPS || max(temp) > rangeval[2]+EPS) {
warning(paste("Values in argument 'evalarg' are outside ",
"of permitted range and will be ignored."))
print(c(rangeval[1]-min(temp), max(temp) - rangeval[2]))
}
# get maximum number of evaluation values
if (is.vector(evalarg)) {
n <- length(evalarg)
} else {
n <- evaldim[1]
}
# Set up coefficient array for FD
coef <- fdobj$coefs
coefd <- dim(coef)
ndim <- length(coefd)
if (ndim <= 1) nrep <- 1 else nrep <- coefd[2]
if (ndim <= 2) nvar <- 1 else nvar <- coefd[3]
# check coef is conformable with evalarg
if(length(evaldim)>1){
if(evaldim[2]==1){
evalarg <- c(evalarg)
} else {
if(evaldim[2] != coefd[2]){
stop('evalarg has ', evaldim[2], ' columns; does not match ',
ndim[2], ' = number of columns of ffdobj$coefs')
}
}
}
# Set up array for function values
if (ndim <= 2) {
evalarray <- matrix(0,n,nrep)
} else evalarray <- array(0,c(n,nrep,nvar))
if (ndim == 2) dimnames(evalarray) <- list(NULL,dimnames(coef)[[2]])
if (ndim == 3)
dimnames(evalarray) <- list(NULL,dimnames(coef)[[2]],
dimnames(coef)[[3]])
# Case where EVALARG is a vector of values to be used for all curves
if (is.vector(evalarg)) {
evalarg[evalarg < rangeval[1]-1e-10] <- NA
evalarg[evalarg > rangeval[2]+1e-10] <- NA
basismat <- eval.basis(evalarg, basisobj, Lfdobj, returnMatrix)
# evaluate the functions at arguments in EVALARG
if (ndim <= 2) {
evalarray <- basismat %*% coef
# needed because dimnames may malfunction with Matrix basismat
dimnames(evalarray) <- list(rownames(basismat), colnames(coef))
} else {
evalarray <- array(0,c(n,nrep,nvar))
for (ivar in 1:nvar) evalarray[,,ivar] <- basismat %*% coef[,,ivar]
}
} else {
# case of evaluation values varying from curve to curve
for (i in 1:nrep) {
evalargi <- evalarg[,i]
if (all(is.na(evalargi))) stop(
paste("All values are NA for replication",i))
index <- !(is.na(evalargi) | evalargi < rangeval[1] |
evalargi > rangeval[2])
evalargi <- evalargi[index]
basismat <- eval.basis(evalargi, basisobj, Lfdobj, returnMatrix)
# evaluate the functions at arguments in EVALARG
if (ndim == 2) {
evalarray[ index, i] <- as.vector(basismat %*% coef[,i])
evalarray[!(index),i] <- NA
}
if (ndim == 3) {
for (ivar in 1:nvar) {
evalarray[ index,i,ivar] <-
as.vector(basismat %*% coef[,i,ivar])
evalarray[!(index),i,ivar] <- NA
}
}
}
}
if((length(dim(evalarray))==2) && !returnMatrix) {
return(as.matrix(evalarray))
} else return(evalarray)
}