Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion DESCRIPTION
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,6 @@ Suggests:
License: GPL-3
Encoding: UTF-8
LazyData: true
RoxygenNote: 6.1.1
RoxygenNote: 7.3.2
VignetteBuilder: knitr
Language: en-GB
3 changes: 3 additions & 0 deletions NAMESPACE
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
# Generated by roxygen2: do not edit by hand

export(CKiD_U25_combined_US)
export(CKiD_U25_creatinine_US)
export(CKiD_U25_cystatin_US)
export(apri)
export(bar_score)
export(bilirubin_to_SI)
Expand Down
119 changes: 119 additions & 0 deletions R/egfr.R
Original file line number Diff line number Diff line change
Expand Up @@ -271,3 +271,122 @@ ibw = function(height, sex) {
height = height / 100
height ^ 2 * bmivar
}


#' Creatinine based eGFR by CKiD U25 equation (US units)
#'
#' Reference: Pierce CB, Muñoz A, Ng DK, Warady BA, Furth SL, Schwartz GJ.
#' Age- and sex-dependent clinical equations to estimate glomerular filtration
#' rates in children and young adults with chronic kidney disease. Kidney
#' International. 2021;99(4):948–956. doi:10.1016/j.kint.2020.10.047
#'
#' @param creat numeric vector of creatinine levels in mg/dl
#' @param age numeric vector of ages in years
#' @param sex character vector of sex ("F" = female, "M" = male)
#' @param height numeric vector of heights in cm
#'
#' @return numeric vector of eGFR in ml/min/1.73m²
#' @export
#'
#' @examples
#' CKiD_U25_creatinine_US(creat = 1, age = 12, sex = "F", height = 132)
CKiD_U25_creatinine_US = function(creat, age, sex, height){

if ( (min(age)<1) | (max(age)>25)) cat("\nWarning: there are age values <1 or >25 years; for those children, eGFR values might be invalid\n")

coeff <- if(age < 12){
if(sex == "F") 36.1 * 1.008 ^ (age - 12)
else 39 * 1.008 ^ (age - 12)
} else if (age < 18) {
if(sex == "F") 36.1 * 1.023 ^ (age - 12)
else 39 * 1.045 ^ (age - 12)
} else {
if(sex == "F") 41.4
else 50.8
}

eGFR <- coeff * (height / 100) / creat
round(eGFR, 1)
}

#' Cystatin C based eGFR by CKiD U25 equation (US units)
#'
#' Reference: Pierce CB, Muñoz A, Ng DK, Warady BA, Furth SL, Schwartz GJ.
#' Age- and sex-dependent clinical equations to estimate glomerular filtration
#' rates in children and young adults with chronic kidney disease. Kidney
#' International. 2021;99(4):948–956. doi:10.1016/j.kint.2020.10.047
#'
#' @param cystatin numeric vector of Cystatin C levels in mg/L
#' @param age numeric vector of ages in years
#' @param sex character vector of sex ("F" = female, "M" = male)
#'
#' @return numeric vector of eGFR in ml/min/1.73m²
#' @export
#'
#' @examples
#' CKiD_U25_cystatin_US(cystatin = 1, age = 18, sex = "F")
CKiD_U25_cystatin_US = function(cystatin, age, sex){

if ( (min(age)<1) | (max(age)>25)) cat("\nWarning: there are age values <1 or >25 years; for those children, eGFR values might be invalid\n")

coeff <- if(age < 12){
if(sex == "F") 79.9*1.004 ^ (age - 12)
else 87.2 * 1.011 ^ (age - 15)
} else if(age < 15) {
if(sex == "F") 79.9 * 0.974 ^ (age - 12)
else 87.2 * 1.011 ^ (age-15)
} else if (age < 18) {
if(sex == "F") 79.9*0.974 ^ (age - 12)
else 87.2 * 0.960 ^ (age - 15)
} else {
if(sex == "F") 77.1
else 68.3
}

eGFR <- coeff / cystatin
round(eGFR, 1)
}

#' Cystatin C and serum Creatinine based eGFR by CKiD U25 equation (US units)
#'
#' Wrapper function for estimating pediatric GFR based on data from the CKiD
#' study of children with CKD. Calculates a Cystatin C-based and Creatinine-
#' based eGFR then averages them. This has been shown to more faithfully
#' estimate measured GFR than either equation separately
#'
#' Reference: Pierce CB, Muñoz A, Ng DK, Warady BA, Furth SL, Schwartz GJ.
#' Age- and sex-dependent clinical equations to estimate glomerular filtration
#' rates in children and young adults with chronic kidney disease. Kidney
#' International. 2021;99(4):948–956. doi:10.1016/j.kint.2020.10.047
#'
#' @param cystatin numeric vector of Cystatin C levels in mg/dl
#' @param creat numeric vector of creatinine levels in mg/dl
#' @param age numeric vector of ages in years
#' @param sex character vector of sex ("F" = female, "M" = male)
#' @param height numeric vector of heights in cm
#' @param verbose a single boolean value. If true, return all the component
#' parts of the eGFR (cystatin, cr, combined), if false (defult), only return
#' the combined eGFR
#'
#' @return numeric vector of eGFR in ml/min/1.73m²
#' @export
#'
#' @examples
#' CKiD_U25_combined_US(cystatin = 1, creat = 0.7, age = 18, sex = "F",
#' height = 132, verbose = FALSE)
CKiD_U25_combined_US = function(cystatin, creat, age, sex, height,
verbose = FALSE){

eGFRU25.cr <- CKiD_U25_creatinine_US(creat = creat, age = age,
height = height, sex = sex)
eGFRU25.cys <- CKiD_U25_cystatin_US(cystatin = cystatin, age = age, sex = sex)
eGFRU25.avg <- (eGFRU25.cys + eGFRU25.cr) / 2

## Determine if we should return all the component parts or just the result
## of the combined calculation
if(verbose) {
return(round(cbind(eGFRU25.cr, eGFRU25.cys, eGFRU25.avg),1))
} else {
return(round(eGFRU25.avg, 1))
}
}
74 changes: 47 additions & 27 deletions README.Rmd
Original file line number Diff line number Diff line change
@@ -1,57 +1,76 @@
---
title: "transplantr"
title: "transplantr CKiD"
output: github_document
---

```{r setup, include=FALSE}
knitr::opts_chunk$set(echo = TRUE, eval = FALSE)
knitr::opts_chunk$set(echo = TRUE)
```

The _transplantr_ package provides a set of vectorised functions for audit and clinical research in solid organ transplantation. These are particularly intended to work well with multiple datapoints in large series of data, where manual calculations would be particularly tedious.
The *transplantr* package provides a set of vectorised functions for audit and clinical research in solid organ transplantation. These are particularly intended to work well with multiple datapoints in large series of data, where manual calculations would be particularly tedious.

The functions provided fall into three groups:

* Donor and recipient risk indices
* HLA mismatch level calculators
* Estimated GFR calculators
* Biochemical unit converters
- Donor and recipient risk indices
- HLA mismatch level calculators
- Estimated GFR calculators
- Biochemical unit converters

Although the package was built with unit tests, inaccuracies cannot be completely excluded. it is not a medical device and should not be used for making clinical decisions.

## transplantr-CKiDu25

You are viewing a fork of the [main CRAN transplantr package](https://cran.r-project.org/web/packages/transplantr/index.html "CRAN repository for transplantr package") updated to include functions for calculating pediatric eGFR based on the following publication:

Pierce CB, Muñoz A, Ng DK, Warady BA, Furth SL, Schwartz GJ. **Age- and sex-dependent clinical equations to estimate glomerular filtration rates in children and young adults with chronic kidney disease.** *Kidney International*. 2021;99(4):948–956. [doi:10.1016/j.kint.2020.10.047](https://doi.org/10.1016/j.kint.2020.10.047 "Persistent DOI link for Pierce et al. paper")

# Installation

transplantr can be installed from CRAN:
This version of transplantr can be installed from github:

```{r}
```{r echo=TRUE, message=FALSE, warning=FALSE}
# install transplantr
install.packages("transplantr")
devtools::install_github("xgaeta/transplantr-CKiDu25")

# load transplantr once installed
library(transplantr)
```

## Development version

The development version can be installed from GitHub, if you want all the latest features, together with all the latest bugs and errors. Installing from CRAN is the best option for most users as the submitted packages have to pass some very pedantic automated tests before they can be hosted on CRAN. If you do want the _caveat emptor_, you have been warned version, this is how:
These new equations follow the same style as the rest of the package, including sex as a binary variable. Height is provided in cm. They currently use US based equations. Outputs are in mL/min/1.73m^2^.t

```{r}
# install from GitHub
devtools::install_packages("johnasher/transplantr")
```{r echo=TRUE}
CKiD_U25_cystatin_US(cystatin = 1.2, age = 9.5, sex = "F")

CKiD_U25_creatinine_US(creat = 0.8, age = 9.5, sex = "F", height = 132)

CKiD_U25_combined_US(cystatin = 1.2, creat = 0.8, age = 9.5, sex = "F", height = 132, verbose = TRUE)
```

# Tips on using _transplantr_
[Pull requests have been filed](https://github.com/johnasher/transplantr/pull/5 "Current status of CKiD U25 pull request") to merge these equations into the main [transplantr](https://github.com/johnasher/transplantr/ "Github repository for original transplantr package, currently v0.2.0") package

## Remainder of the base *transplantr* Readme is included below:

As vectorised functions, the functions can be applied across a whole dataset fairly rapidly. I find that the easiest way to do this is using a "pipe" of functions from the _dplyr_ package. _dplyr_ can be installed on its own or, as I would recommend, by installing the whole _tidyverse_ family of packages - a family which includes the legendary _ggplot2_ graphing package.
------------------------------------------------------------------------

```{r}
# Tips on using *transplantr*

As vectorised functions, the functions can be applied across a whole dataset fairly rapidly. I find that the easiest way to do this is using a "pipe" of functions from the *dplyr* package. *dplyr* can be installed on its own or, as I would recommend, by installing the whole *tidyverse* family of packages - a family which includes the legendary *ggplot2* graphing package.

```{r eval=FALSE, message=FALSE, warning=FALSE, include=TRUE}
# install whole tidyverse
install.packages("tidyverse")

# install just dplyr
install.packages("dplyr")
```
```{r include=FALSE}
library(dplyr)
```

Although recommended, _dplyr_ is not necessary for most _transplantr_ functions to work. _dplyr_ is needed for the EPTS and KDPI functions, and additionally _stringr_ is needed for the `hla_mm_level_str()` function and also for the `chi2dob()` function, one unlikely to be needed by anyone working outside Scotland!

Although recommended, *dplyr* is not necessary for most *transplantr* functions to work. *dplyr* is needed for the EPTS and KDPI functions, and additionally *stringr* is needed for the `hla_mm_level_str()` function and also for the `chi2dob()` function, one unlikely to be needed by anyone working outside Scotland!

## Biochemical units

Expand All @@ -61,23 +80,24 @@ Albumin is generally reported in g/l in the UK, but more commonly as g/dl in the

Which is the best option to use? Calling the wrapper function uses fewer keystrokes so is quicker to type, but as it is a function calling another function, there is a slight increase in computational overhead.

## Using _transplantr_ functions with _dplyr_
## Using *transplantr* functions with *dplyr*

Let's say you want to calculate MELD scores for a series of liver transplant candidates. OK, you probably actually want MELD-Na, but let's go with MELD as it has fewer variables! The data is in a dataframe or tibble called "oltx.assessments" and the relevant variables are Patient.INR, Patient.Bilirubin, Patient.Creatinine and Patient.Dialysed. To add a new Patient.MELD variable to the dataframe, you would use a _dplyr_ pipe with the `mutate()` verb:
Let's say you want to calculate MELD scores for a series of liver transplant candidates. OK, you probably actually want MELD-Na, but let's go with MELD as it has fewer variables! The data is in a dataframe or tibble called "oltx.assessments" and the relevant variables are Patient.INR, Patient.Bilirubin, Patient.Creatinine and Patient.Dialysed. To add a new Patient.MELD variable to the dataframe, you would use a *dplyr* pipe with the `mutate()` verb:

```{r}
oltx.assessments <- oltx.assessments %>%
```{r eval=FALSE, include=TRUE}
oltx.assessments <- oltx.assessments |>
mutate(Patient.MELD = meld(INR = Patient.INR, bili = Patient.Bilirubin,
creat = Patient.Creatinine, dialysis = Patient.Dialysed, units = "SI"))

```

The `units = "SI"` can be left out provided that creatinine and bilirubin are both in µmol/l. To switch to mg/dl, use `units = "US"` or call `meld_US()` instead.

## Using _transplantr_ functions with base R
## Using *transplantr* functions with base R

Although I think _dplyr_ makes life much easier when organising data, I concede that some people prefer to use base R functions instead. Using a vectorised function with multiple vector inputs is not easy in base R but can be done with the `mapply()`, or more easily with the `pmap_dbl()` from the _purrr_ package.
Although I think *dplyr* makes life much easier when organising data, I concede that some people prefer to use base R functions instead. Using a vectorised function with multiple vector inputs is not easy in base R but can be done with the `mapply()`, or more easily with the `pmap_dbl()` from the *purrr* package.

```{r}
```{r eval=FALSE, include=TRUE}
# attach oltx.assessments to save a lot of typing!
attach(oltx.assessments)

Expand All @@ -96,13 +116,13 @@ oltx.assessments$Patient.MELD = mapply(FUN = meld, Patient.INR, Patient.Bilirubi
detach(oltx.assessments)
```

The advantage of using a _dplyr_ pipe, apart from easier code, is speed. Benchmarking on a basic Linux laptop showed that the median time to perform vectorised calculation of 100,000 MELD scores was 115 milliseconds, compared with 6007 milliseconds using ``pmap_dbl()` and 6484 with `mapply()`.
The advantage of using a *dplyr* pipe, apart from easier code, is speed. Benchmarking on a basic Linux laptop showed that the median time to perform vectorised calculation of 100,000 MELD scores was 115 milliseconds, compared with 6007 milliseconds using \``pmap_dbl()` and 6484 with `mapply()`.

## Using the functions with a single case

Although vectorised functions for multiple calculations are one of the best features of R, you might just want to collect data on a single case. This is very straightforward:

```{r}
```{r eval=FALSE, include=TRUE}
# using µmol/l
meld(INR = 2.1, bili = 34, creat = 201, dialysis = 0)

Expand Down
Loading