| Title: | Detect the Shape of Dose-Response Curves |
|---|---|
| Description: | Provides functions for hormesis screening by classifying the shapes of dose-response curves based on semiparametric tests. The shapes are indications of different potential toxicology effect. It also offers a scalable visualization scheme to present testing conclusions for large-scale dataset with a large number of dose-response curves. For more information, see Jin et al. (2026) <https://github.com/YinglJin-0203/shorm/blob/main/Manuscripts/BotanicalHormesisTestingFinalDraft.docx>. |
| Authors: | Eric Bair [aut, cre], Ying Jin [aut, cph] |
| Maintainer: | Eric Bair <[email protected]> |
| License: | GPL-3 |
| Version: | 0.1.3 |
| Built: | 2026-05-26 18:21:25 UTC |
| Source: | https://github.com/yingljin-0203/shorm |
The SHARP shape detection test relies on a underlying random generation process, which may lead to ambiguous test results. To examin its uncertainty and obtain a more robust conclusion, we may with to repet the test on the same data.
RepeatSHARP(df, nRep, mixed = FALSE, xName, yName, rName, niter = 1000)RepeatSHARP(df, nRep, mixed = FALSE, xName, yName, rName, niter = 1000)
df |
Dose-response curve data in a table format. Dose and responses should be two separate columns with numeric values. |
nRep |
Number of repetitions of SHAPR test. Integer. |
mixed |
Logical indicator (TRUE for FALSE) for whether or not to use the mixed-model-based test. |
xName |
The column name for dose. Character string. |
yName |
The column name for response. Character string. |
rName |
The column name for random effect. Only used if mixed = TRUE. Character string.git a |
niter |
An integer for the number of iterations in SHARP test procedure |
A dataframe of test results from all repititions. Each row is one single test with four p values after Holm adjustment.
# Simulate dose-response data x <- seq(0, 1, length.out = 48) y <- 2*sqrt(x)+rnorm(48) y[17:32] <- y[17:32]+0.5 y[33:48] <- y[33:48]+1 curve <- data.frame(x, y) curve$rep <- rep(1:3, each = 16) # Fixed-model based test RepeatSHARP(curve, nRep = 10, xName = "x", yName = "y", niter = 10) # Mixed-model based test RepeatSHARP(curve, nRep = 10, mixed = TRUE, xName = "x", yName = "y", rName = "rep", niter = 10)# Simulate dose-response data x <- seq(0, 1, length.out = 48) y <- 2*sqrt(x)+rnorm(48) y[17:32] <- y[17:32]+0.5 y[33:48] <- y[33:48]+1 curve <- data.frame(x, y) curve$rep <- rep(1:3, each = 16) # Fixed-model based test RepeatSHARP(curve, nRep = 10, xName = "x", yName = "y", niter = 10) # Mixed-model based test RepeatSHARP(curve, nRep = 10, mixed = TRUE, xName = "x", yName = "y", rName = "rep", niter = 10)
Function to visualize SHARP test results
SharpScatter( pinc, pdec, pconc, pconv, alpha = 0.05, scale = "log", label = NULL, size_point = 2, size_label = 5, ... )SharpScatter( pinc, pdec, pconc, pconv, alpha = 0.05, scale = "log", label = NULL, size_point = 2, size_label = 5, ... )
pinc, pdec, pconc, pconv
|
SHARP test p-values corresponding to increasing, decreasing, concave and convex |
alpha |
significance threshold. alpha=NULL corresponding to no significance threshold |
scale |
how axis should be scaled for better visual presentation. Choose between none, log and linear. Please see details for the transformation fomula. |
label |
labels of the point to visualize. label=NULL means no labeling. |
size_point, size_label
|
the size of points and label. size_lable is used when label is not NULL. |
... |
additional parameters passed to ggplot |
The shape scatter plot represents the four p-values (corresponding to four shape types) of SHARP test on a 2D space. it can not only visualize the conclusions of the test, but also the confidence level of the test. The plot surface is divided into two parts along two perpendicular directions, corresponding to two opposite shapes. The coordinates of points are derived from p-values such that:
Inconclusive shapes are placed in the center area within the significance thresholds (p > 0.05)
Significant shapes are placed in the edge area out of the significance thresholds (p < 0.05)
The closer points are to the significance thresholds, the more ambiguous shape conclusion is
Axis can be scaled for better visual presentation. When scale = "log", a log-based transformation is implemented as follows:
where .
When scale = "linear", a piece-wise linear transformation is implemented:
In both case, the significant and insignificant regions are also evenly divided in each test.
The plotted ggplot object
# Simulate dose-response data x <- seq(0, 1, length.out = 48) y <- 2*sqrt(x)+rnorm(48) y[17:32] <- y[17:32]+0.5 y[33:48] <- y[33:48]+1 curve <- data.frame(x, y) curve$rep <- rep(1:3, each = 16) # Fixed-model based test sharpt <- SHARPtest(curve, xName = "x", yName = "y", niter = 100) # Plot the graph SharpScatter(sharpt[1], sharpt[2], sharpt[3], sharpt[4], niter = 100)# Simulate dose-response data x <- seq(0, 1, length.out = 48) y <- 2*sqrt(x)+rnorm(48) y[17:32] <- y[17:32]+0.5 y[33:48] <- y[33:48]+1 curve <- data.frame(x, y) curve$rep <- rep(1:3, each = 16) # Fixed-model based test sharpt <- SHARPtest(curve, xName = "x", yName = "y", niter = 100) # Plot the graph SharpScatter(sharpt[1], sharpt[2], sharpt[3], sharpt[4], niter = 100)
Implement SHARP test once on a dose-response curve
SHARPtest(df, mixed = FALSE, xName, yName, rName, niter = 1000)SHARPtest(df, mixed = FALSE, xName, yName, rName, niter = 1000)
df |
Dose-response curve data in a table format. Dose and responses should be two separate columns with numeric values. |
mixed |
Logical indicator (TRUE for FALSE) for whether or not to use the mixed-model-based test. |
xName |
The column name for dose. Character string. |
yName |
The column name for response. Character string. |
rName |
The column name for random effect. Only used if mixed = TRUE. Character string. |
niter |
An integer for the number of iterations in SHARP test procedure. |
A vector of four p values after Holm adjustment, indicating the significance of four different shapes types.
# Simulate dose-response data x <- seq(0, 1, length.out = 48) y <- 2*sqrt(x)+rnorm(48) y[17:32] <- y[17:32]+0.5 y[33:48] <- y[33:48]+1 curve <- data.frame(x, y) curve$rep <- rep(1:3, each = 16) # Fixed-model based test SHARPtest(curve, xName = "x", yName = "y", niter = 100) # Mixed-model based test SHARPtest(curve, mixed = TRUE, xName = "x", yName = "y", rName = "rep", niter = 100)# Simulate dose-response data x <- seq(0, 1, length.out = 48) y <- 2*sqrt(x)+rnorm(48) y[17:32] <- y[17:32]+0.5 y[33:48] <- y[33:48]+1 curve <- data.frame(x, y) curve$rep <- rep(1:3, each = 16) # Fixed-model based test SHARPtest(curve, xName = "x", yName = "y", niter = 100) # Mixed-model based test SHARPtest(curve, mixed = TRUE, xName = "x", yName = "y", rName = "rep", niter = 100)