-
Notifications
You must be signed in to change notification settings - Fork 4
/
logistf.fit.R
123 lines (109 loc) · 3.25 KB
/
logistf.fit.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
logistf.fit <- function(
x,
y,
weight=NULL,
offset=NULL,
firth=TRUE,
init=NULL,
control,
modcontrol,
standardize = FALSE,
...
) {
n <- nrow(x)
k <- ncol(x)
collapse <- control$collapse
coll <- FALSE
if (is.null(init)) init=rep(0,k)
if (is.null(offset)) offset=rep(0,n)
if (is.null(weight)) weight=rep(1,n)
if (missing(control)) control<-logistf.control()
if (missing(modcontrol)) modcontrol<-logistf.mod.control()
tau <- modcontrol$tau
if (!is.numeric(tau) | length(tau)>1){
stop("Invalid value for degree of penalization tau: Must be numeric.")
}
col.fit <- modcontrol$terms.fit
if(is.null(col.fit)){
col.fit <- 1:k
}
if(collapse && isTRUE(all.equal(weight, rep(1, length(weight))))) {
xy <- cbind(x,y)
temp <- unique(unlist(sapply(1:ncol(xy), function(X) unique(xy[, X]))))
if(length(temp) <= 10) {
xc <- uniquecombs(cbind(x,y,offset))
xorig <- x
yorig <- y
weight <- table(attr(xc, "index"))
x <- xc[,1:k]
y <- xc[,k+1]
if(!is.null(offset))
offset<-xc[,k+2]
n <- nrow(xc)
coll <- TRUE
}
}
if(standardize){
sdx <- apply(x, 2, sd)
sdx[sdx==0] <- 1
x <- x %*% diag(1/sdx)
init <- init * sdx
}
if (col.fit[1]==0) maxit<-0 #only evaluate likelihood and go back
else maxit<-control$maxit
maxstep<-control$maxstep
maxhs<-control$maxhs
lconv<-control$lconv
gconv<-control$gconv
xconv<-control$xconv
fit <- control$fit
beta <- init
firth <- if(firth) 1 else 0
ncolfit <- length(col.fit)
covar <- matrix(0, k, k)
Ustar <- double(k)
pi <- double(n)
Hdiag <- double(n)
loglik <- evals <- iter <- warning_prob <- 0
conv <- double(3)
mode(x) <- mode(weight) <- mode(beta) <- mode(offset) <- "double"
mode(y) <- mode(firth) <- mode(n) <- mode(k) <- "integer"
mode(maxstep) <- mode(lconv) <- mode(gconv) <- mode(xconv) <- mode(tau) <- "double"
mode(loglik) <- "double"
mode(col.fit) <- mode(ncolfit) <- mode(maxit) <- mode(maxhs) <- "integer"
mode(evals) <- mode(iter) <- mode(warning_prob) <- "integer"
res <- switch(fit,
IRLS = .C(
"logistffit_IRLS",
x, y, n, k, weight, offset, beta=beta, col.fit, ncolfit,
firth, maxit, maxstep, maxhs, lconv, gconv, xconv, tau,
var=covar, pi=pi, Hdiag=Hdiag, loglik=loglik, evals=evals, iter=iter, conv=conv, warning_prob = warning_prob,
PACKAGE="logistf"
),
NR = .C(
"logistffit_revised",
x, y, n, k, weight, offset, beta=beta, col.fit, ncolfit,
firth, maxit, maxstep, maxhs, lconv, gconv, xconv, tau,
var=covar, Ustar=Ustar, pi=pi, Hdiag=Hdiag,
loglik=loglik, evals=evals, iter=iter, conv=conv, warning_prob = warning_prob,
PACKAGE="logistf"
)
)
if(warning_prob){
warning("fitted probabilities numerically 0 or 1 occurred")
}
if(coll) {
res$pi<-res$pi[attr(xc,"index")]
res$Hdiag<-as.numeric((res$Hdiag/weight)[attr(xc,"index")])
}
if(standardize){
res$beta <- res$beta / sdx
res$var <- res$var %*% diag(1/sdx)
}
res <- res[c("beta", "var", "Ustar", "pi", "Hdiag", "loglik",
"evals", "iter", "conv", "warning_prob", "tau")]
res
}
.onUnload <- function (libpath) {
library.dynam.unload("logistf", libpath)
}