Skip to content

Commit e3626fb

Browse files
committed
added tests for binomial and poisson data
1 parent 09d15ba commit e3626fb

2 files changed

Lines changed: 103 additions & 16 deletions

File tree

OpenStats/R/Backend_LC50.R

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -148,11 +148,20 @@ check_fit <- function(model, ic_percentage, min_conc, max_conc,
148148
Problems <- paste(Problems,
149149
"IC lower than lowest measured concentration", collapse = " , "
150150
)
151+
} else if (type != "continuous") {
152+
Problems <- paste(
153+
Problems,
154+
"Global p-value not available for non-continuous drm fits"
155+
)
151156
}
152157

153158
IC_relative_lower <- ed_res[1, 3]
154159
IC_relative_higher <- ed_res[1, 4]
155-
p_value <- drc::noEffect(model)[3]
160+
if (type == "continuous") {
161+
p_value <- drc::noEffect(model)[3]
162+
} else {
163+
p_value <- NA
164+
}
156165
Response_lowestdose_predicted <- env_lc_V1_2$shapenumber(Response_lowestdose_predicted)
157166
Response_highestdose_predicted <- env_lc_V1_2$shapenumber(Response_highestdose_predicted)
158167
HillCoefficient <- env_lc_V1_2$shapenumber(HillCoefficient)

OpenStats/inst/tinytest/test_Backend_DoseResponse.R

Lines changed: 93 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,42 @@
11
library(tinytest)
22

3-
simulate <- function(name, slope, true_ic50) {
3+
# Test check_fit
4+
simulate_poisson <- function(name, slope, true_ic50) {
5+
b <- slope # slope
6+
c <- 0.05 # lower limit
7+
d <- 1.1 # upper limit
8+
e <- true_ic50 # IC50
9+
set.seed(42)
10+
conc_levels <- c(0.1, seq(2.5, 26, by = 2.5))
11+
conc <- rep(conc_levels, each = 5)
12+
logistic_response <- function(conc, b, c, d, e) {
13+
c + (d - c) / (1 + (conc / e)^b)
14+
}
15+
probs <- logistic_response(conc, b, c, d, e) * 100
16+
abs <- rpois(length(conc), lambda = probs)
17+
data.frame(
18+
substance = rep(name, length(conc)), conc = conc, abs = abs, unit = "M"
19+
)
20+
}
21+
simulate_binomial <- function(name, slope, true_ic50) {
22+
b <- slope # slope
23+
c <- 0.05 # lower limit
24+
d <- 1.1 # upper limit
25+
e <- true_ic50 # IC50
26+
set.seed(42)
27+
conc_levels <- c(0.1, seq(2.5, 26, by = 2.5))
28+
conc <- rep(conc_levels, each = 5)
29+
logistic_response <- function(conc, b, c, d, e) {
30+
c + (d - c) / (1 + (conc / e)^b)
31+
}
32+
probs <- logistic_response(conc, b, c, d, e)
33+
probs <- probs / max(probs)
34+
abs <- rbinom(length(conc), 1, probs)
35+
data.frame(
36+
substance = rep(name, length(conc)), conc = conc, abs = abs, unit = "M"
37+
)
38+
}
39+
simulate_continous <- function(name, slope, true_ic50) {
440
# Define true parameters
541
b <- slope # slope
642
c <- 0.05 # lower limit
@@ -21,35 +57,77 @@ simulate <- function(name, slope, true_ic50) {
2157
substance = rep(name, length(conc)), conc = conc, abs = abs, unit = "M"
2258
)
2359
}
24-
25-
# Test check fit
26-
test_check_fit <- function(ic50_true) {
27-
df <- simulate("A", 7, ic50_true)
60+
simulate <- function(name, slope, true_ic50, type) {
61+
if (type == "continous") {
62+
simulate_continous(name, slope, true_ic50)
63+
} else if (type == "binomial") {
64+
simulate_binomial(name, slope, true_ic50)
65+
} else if (type == "Poisson") {
66+
simulate_poisson(name, slope, true_ic50)
67+
} else {
68+
stop("Encountered unknown type", type)
69+
}
70+
}
71+
test_check_fit <- function(ic50_true, ic_percentage, type) {
72+
ic50_true <- 10
73+
ic_percentage <- 50
74+
type <- "Poisson"
75+
df <- simulate("A", 7, ic50_true, type)
2876
model <- drc::drm(abs ~ conc,
2977
data = df, fct = drc::LL.4(),
30-
robust = "median"
78+
robust = "median", type = type
3179
)
32-
valid_points <- OpenStats:::false_discovery_rate(model, "continuous")
80+
valid_points <- OpenStats:::false_discovery_rate(model, type)
3381
model <- drc::drm(abs ~ conc,
3482
data = df,
3583
subset = valid_points,
3684
start = model$coefficients,
3785
fct = drc::LL.4(), robust = "mean",
86+
type = type
3887
)
88+
ed_res <- drc::ED(
89+
model,
90+
respLev = ic_percentage,
91+
interval = "delta",
92+
level = 0.95,
93+
type = "relative",
94+
display = FALSE
95+
)
96+
expected <- ed_res[[1L]]
3997
conc <- "conc"
40-
abs <- "abs"
98+
y <- "abs"
4199
title = "Bla"
42100
res <- OpenStats:::check_fit(
43-
model, 50, min(df[, conc]),
44-
max(df[, conc]), min(df[, abs]), max(df[, abs]), title, "M", "continuous"
101+
model, ic_percentage, min(df[, conc]),
102+
max(df[, conc]), min(df[, y]), max(df[, y]), title, "M", type
45103
)
104+
got <- res[[7]]
105+
rel_error <- function(a, b) {
106+
abs(b - a) / b
107+
}
108+
tol_percentage <- 0.1
109+
expect_true(rel_error(got, expected) < tol_percentage)
46110
expect_true(is.data.frame(res))
47111
}
48-
test_check_fit(10)
112+
test_check_fit(10, 50, "binomial")
113+
test_check_fit(10, 25, "binomial")
114+
test_check_fit(10, 75, "binomial")
115+
test_check_fit(2, 50, "binomial")
116+
117+
test_check_fit(10, 50, "Poisson")
118+
test_check_fit(10, 25, "Poisson")
119+
test_check_fit(10, 75, "Poisson")
120+
test_check_fit(2, 50, "Poisson")
121+
122+
test_check_fit(10, 25, "continous")
123+
test_check_fit(10, 1, "continous")
124+
test_check_fit(10, 50, "continous")
125+
test_check_fit(10, 75, "continous")
126+
test_check_fit(10, 99, "continous")
49127

50128
# Test ic50 internal
51129
test_ic50_internal <- function(ic50_true) {
52-
data <- simulate("A", 7, ic50_true)
130+
data <- simulate("A", 7, ic50_true, "continous")
53131
res <- OpenStats:::ic_internal(data, 50, "abs", "conc", "substance", FALSE, FALSE, "M", "continuous")
54132
res_df <- res[[1]]
55133
tol_percentage <- 0.1
@@ -138,7 +216,7 @@ test_rsdr()
138216
# Test cases for env_lc_V1_2$false_discovery_rate
139217
test_false_discovery_rate <- function() {
140218
checks <- list()
141-
df <- simulate("A", 7, 10)
219+
df <- simulate("A", 7, 10, "continous")
142220
model <- drc::drm(abs ~ conc, data = df, fct = drc::LL.4(), robust = "median")
143221
include <- OpenStats:::false_discovery_rate(model, "continuous")
144222
checks[[1]] <- expect_true(is.logical(include))
@@ -149,7 +227,7 @@ test_false_discovery_rate()
149227

150228
# drawplot_only_raw_data
151229
test_drawplot_only_raw_data <- function() {
152-
df <- simulate("A", 7, 2)
230+
df <- simulate("A", 7, 2, "continous")
153231
p <- OpenStats:::drawplot_only_raw_data(df, "abs", "conc", "Bla", "M")
154232
layers <- p$layers
155233
expect_true(inherits(layers[[1]]$geom, "GeomBoxplot"))
@@ -172,7 +250,7 @@ test_drawplot_only_raw_data()
172250

173251
# drawplot
174252
test_drawplot <- function() {
175-
df <- simulate("A", 7, 11)
253+
df <- simulate("A", 7, 11, "continous")
176254
model <- drc::drm(abs ~ conc,
177255
data = df, fct = drc::LL.4(),
178256
robust = "median"

0 commit comments

Comments
 (0)