Skip to content

Commit

Permalink
Merge pull request #6 from alwinw/dev/aki-calc
Browse files Browse the repository at this point in the history
Added aki.units() method
  • Loading branch information
alwinw committed Oct 18, 2020
2 parents 59991ee + b81fe3a commit 8c48544
Show file tree
Hide file tree
Showing 7 changed files with 166 additions and 20 deletions.
1 change: 1 addition & 0 deletions .Rbuildignore
Expand Up @@ -14,3 +14,4 @@
^\.png$
^README_cache/
^codecov\.yml$
^resources$
8 changes: 6 additions & 2 deletions DESCRIPTION
Expand Up @@ -21,12 +21,16 @@ License: MIT + file LICENSE
URL: https://github.com/alwinw/epocakir
BugReports: https://github.com/alwinw/epocakir/issues
Depends:
R
R (>= 3.5.0)
Imports:
dplyr,
tidyselect,
tibble,
forcats
forcats,
ellipsis,
rlang,
units,
lubridate
Suggests:
testthat,
covr
Expand Down
1 change: 1 addition & 0 deletions NAMESPACE
Expand Up @@ -3,4 +3,5 @@
S3method(aki,default)
S3method(aki,numeric)
S3method(aki,ts)
S3method(aki,units)
export(aki)
63 changes: 53 additions & 10 deletions R/aki.R
@@ -1,24 +1,67 @@
.sCr2metric <- function(SCr) {
if (grepl("mol", units::deparse_unit(SCr))) {
return(units::set_units(SCr * units::set_units(113.120, "g/mol"), "mg/dl"))
} else {
return(units::set_units(SCr, "mg/dl"))
}
}

#' Codify AKI from Serum Creatinine and/or Urine Output
#'
#' Some additional details
#' Using KDIGO Clinical Practice Guideline for Acute Kidney Injury
#' Volume 2 | Issue 1 | March 2012
#'
#' @param x numeric number
#' Provided a series of Serum Creatinine readings and/or Urine Output, aki()
#' calculates whether or not a patient has AKI. The staging (1, 2, 3) of AKI is
#' also calculated
#'
#' @return
#' @param data A data.frame with the data needed for serum creatinine (SCr)
#' and/or urine output (UO)
#' @param SCr The variable name, e.g. "cr", to be used for determining
#' AKI based on creatinine level. A numeric vector or time series of
#' serum creatinine values if the data argument is unused
#' @param UO The variable name, e.g. "urine", to be used for determining
#' AKI based on urine output. A numeric vector or time series of
#' urine output values if the data argument is unused
#' @param bCr The variable name, e.g. "baseline_cr", to be used for determining
#' AKI based on urine output. A single numeric value of
#' baseline creatinine if the data argument is unused
#' @param units (character) Units of SCr and UO metric (mg/dl) or SI (umol/l)
#' #TOFIX, consider changing to a list
#' @param na.rm (logical) If TRUE, missing values are removed
#' @param ... Further optional arguments that will be passed to method.
#'
#' @examples
#' aki(seq(60, 200, by = 20))
#' aki(SCr = seq(60, 200, by = 20), bCr = 50)
#' @export
aki <- function(x, ...) {
UseMethod("aki", x)
aki <- function(...) {
ellipsis::check_dots_used()
UseMethod("aki")
}

.aki_stages <- factor(c("AKI Stage 1", "AKI Stage 2", "AKI Stage 3", "No AKI"))

#' @rdname aki
#' @export
aki.numeric <- function(SCr, bCr = NULL, na.rm = FALSE) {
aki.numeric <- function(SCr, bCr = NULL, units = "umol/l", na.rm = FALSE, ...) {
SCr <- units::as_units(SCr, units)
if (is.null(bCr)) {
bCr <- min(SCr, na.rm = na.rm) # Must be run after as_units(SCr, ...)
}
else {
bCr <- units::as_units(bCr, units)
}
aki_stages <- aki.units(SCr = SCr, bCr = bCr, na.rm = na.rm)
return(aki_stages)
}

#' @rdname aki
#' @export
aki.units <- function(SCr, bCr = NULL, na.rm = FALSE, ...) {
if (is.null(bCr)) bCr <- min(SCr, na.rm = na.rm)
aki_stages <- dplyr::case_when(
.sCr2metric(SCr) >= units::set_units(4.0, mg / dl) ~ .aki_stages[3],
SCr >= 3.0 * bCr ~ .aki_stages[3],
SCr >= 2.0 * bCr ~ .aki_stages[2],
SCr >= 1.5 * bCr ~ .aki_stages[1],
Expand All @@ -27,15 +70,15 @@ aki.numeric <- function(SCr, bCr = NULL, na.rm = FALSE) {
return(aki_stages)
}


#' @rdname aki
#' @export
aki.ts <- function(ts_data) {
aki.ts <- function(SCr, UO, units = "umol/l", ...) {

}


#' @rdname aki
#' @export
aki.default <- function(x) {
factor(x, levels = .aki_stages)
aki.default <- function(data, SCr, bCr, units = list("SCr" = "umol/l"), na.rm = FALSE, ...) {
factor(data, levels = .aki_stages)
}
1 change: 1 addition & 0 deletions R/utils.R
@@ -0,0 +1 @@
# set_units(set_units(1:5, mg/dl) * set_units(2, mol/g), mol/l)
46 changes: 38 additions & 8 deletions man/aki.Rd

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

66 changes: 66 additions & 0 deletions tests/testthat/test-aki.R
@@ -1,3 +1,17 @@
test_that(".sCr2metric() conversion 88.4 umol/l to 1mg/dl is correct", {
expect_lte(
abs(.sCr2metric(units::set_units(88.4, "umol/l")) - units::set_units(1, "mg/dl")),
units::set_units(1e-4, "mg/dl")
)
})

test_that(".sCr2metric() conversion 353.6 umol/l to 4mg/dl is correct", {
expect_lte(
abs(.sCr2metric(units::set_units(353.6, "umol/l")) - units::set_units(4, "mg/dl")),
units::set_units(1e-4, "mg/dl")
)
})

test_that("aki() for numeric vector of SCr with no baseline", {
SCr <- seq(60, 200, by = 20)
aki_stages <- forcats::fct_c(
Expand Down Expand Up @@ -27,3 +41,55 @@ test_that("aki() for numeric vector of SCr with baseline", {
)
expect_equal(aki(SCr, bCr = 50), aki_stages)
})

test_that("aki() for vector of SCr in mg/dl with no baseline", {
SCr <- units::set_units(seq(1.5, 4.5, by = 0.5), "mg/dl")
aki_stages <- forcats::fct_c(
.aki_stages[length(.aki_stages)],
.aki_stages[length(.aki_stages)],
.aki_stages[1],
.aki_stages[2],
.aki_stages[2],
.aki_stages[3],
.aki_stages[3]
)
expect_equal(aki(SCr), aki_stages)
})

test_that("aki() for vector of SCr in mg/dl with baseline", {
SCr <- units::set_units(seq(2.0, 4.5, by = 0.5), "mg/dl")
bCr <- units::set_units(1.5, "mg/dl")
aki_stages <- forcats::fct_c(
.aki_stages[length(.aki_stages)],
.aki_stages[1],
.aki_stages[2],
.aki_stages[2],
.aki_stages[3],
.aki_stages[3]
)
expect_equal(aki(SCr, bCr), aki_stages)
})

data <- data.frame(
pt_id = c(rep("pt1", 11), rep("pt2", 13)),
dttm = c(
seq(
lubridate::as_datetime("2020-10-18 09:00:00", tz = "Australia/Melbourne"),
lubridate::as_datetime("2020-10-20 09:00:00", tz = "Australia/Melbourne"),
length.out = 11
),
seq(
lubridate::as_datetime("2020-10-18 10:00:00", tz = "Australia/Melbourne"),
lubridate::as_datetime("2020-10-29 10:00:00", tz = "Australia/Melbourne"),
length.out = 13
)
),
SCr = c(
units::set_units(seq(2.0, 4.5, by = 0.25), "mg/dl"),
units::set_units(seq(3.0, 4.2, by = 0.10), "mg/dl")
),
bCr = c(
rep(units::set_units(1.8, "mg/dl"), 11),
rep(units::set_units(3.0, "mg/dl"), 13)
)
)

0 comments on commit 8c48544

Please sign in to comment.