diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index f57d3bae..a4051166 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -97,7 +97,7 @@ pages: script: #- Rscript -e "install.packages('pkgdown', repos = 'https://cran.rstudio.com')" - Rscript -e "devtools::install(build = TRUE, upgrade = FALSE)" - - R -e "pkgdown::build_site(examples = FALSE, override = list(destination = 'public'))" + - R -e "pkgdown::build_site(examples = FALSE, lazy = TRUE, override = list(destination = 'public'))" artifacts: paths: - public diff --git a/DESCRIPTION b/DESCRIPTION index dd487ba3..f00fe5e6 100644 --- a/DESCRIPTION +++ b/DESCRIPTION @@ -1,6 +1,6 @@ Package: AMR -Version: 0.5.0.9020 -Date: 2019-03-02 +Version: 0.5.0.9021 +Date: 2019-03-05 Title: Antimicrobial Resistance Analysis Authors@R: c( person( diff --git a/NAMESPACE b/NAMESPACE index 44c0422e..f55cd80c 100755 --- a/NAMESPACE +++ b/NAMESPACE @@ -81,8 +81,20 @@ export(count_df) export(eucast_exceptional_phenotypes) export(eucast_rules) export(facet_rsi) +export(filter_1st_cephalosporins) +export(filter_2nd_cephalosporins) +export(filter_3rd_cephalosporins) +export(filter_4th_cephalosporins) +export(filter_ab_class) +export(filter_aminoglycosides) +export(filter_carbapenems) +export(filter_cephalosporins) export(filter_first_isolate) export(filter_first_weighted_isolate) +export(filter_fluoroquinolones) +export(filter_glycopeptides) +export(filter_macrolides) +export(filter_tetracyclines) export(first_isolate) export(freq) export(frequency_tbl) diff --git a/R/filter_ab_class.R b/R/filter_ab_class.R new file mode 100644 index 00000000..fed9838a --- /dev/null +++ b/R/filter_ab_class.R @@ -0,0 +1,268 @@ +# ==================================================================== # +# TITLE # +# Antimicrobial Resistance (AMR) Analysis # +# # +# SOURCE # +# https://gitlab.com/msberends/AMR # +# # +# LICENCE # +# (c) 2019 Berends MS (m.s.berends@umcg.nl), Luz CF (c.f.luz@umcg.nl) # +# # +# This R package is free software; you can freely use and distribute # +# it for both personal and commercial purposes under the terms of the # +# GNU General Public License version 2.0 (GNU GPL-2), as published by # +# the Free Software Foundation. # +# # +# This R package was created for academic research and was publicly # +# released in the hope that it will be useful, but it comes WITHOUT # +# ANY WARRANTY OR LIABILITY. # +# Visit our website for more info: https://msberends.gitab.io/AMR. # +# ==================================================================== # + +#' Filter on antibiotic class +#' +#' Filter on specific antibiotic variables based on their class (ATC groups). +#' @param tbl a data set +#' @param ab_class an antimicrobial class, like \code{"carbapenems"} +#' @param result an antibiotic result: S, I or R (or a combination of more of them) +#' @param scope the scope to check which variables to check, can be \code{"any"} (default) or \code{"all"} +#' @param ... parameters passed on to \code{\link[dplyr]{filter_at}} +#' @details The \code{\code{antibiotics}} data set will be searched for \code{ab_class} in the columns \code{atc_group1} and \code{atc_group2} (case-insensitive). Next, \code{tbl} will be checked for column names with a value in any abbreviations, codes or official names found in the \code{antibiotics} data set. +#' @rdname filter_ab_class +#' @importFrom dplyr filter_at %>% select vars any_vars all_vars +#' @importFrom crayon bold blue +#' @export +#' @examples +#' library(dplyr) +#' +#' # filter on isolates that have any result for any aminoglycoside +#' septic_patients %>% filter_aminoglycosides() +#' +#' # this is essentially the same as: +#' septic_patients %>% +#' filter_at(.vars = vars(c("gent", "tobr", "amik", "kana")), +#' .vars_predicate = any_vars(. %in% c("S", "I", "R"))) +#' +#' +#' # filter on isolates that show resistance to ANY aminoglycoside +#' septic_patients %>% filter_aminoglycosides("R") +#' +#' # filter on isolates that show resistance to ALL aminoglycosides +#' septic_patients %>% filter_aminoglycosides("R", "all") +#' +#' # filter on isolates that show resistance to +#' # any aminoglycoside and any fluoroquinolone +#' septic_patients %>% +#' filter_aminoglycosides("R", "any") %>% +#' filter_fluoroquinolones("R", "any") +filter_ab_class <- function(tbl, + ab_class, + result = NULL, + scope = "any", + ...) { + scope <- scope[1L] + if (is.null(result)) { + result <- c("S", "I", "R") + } + + if (!all(result %in% c("S", "I", "R"))) { + stop("`result` must be one or more of: S, I, R", call. = FALSE) + } + if (!all(scope %in% c("any", "all"))) { + stop("`scope` must be one of: any, all", call. = FALSE) + } + + vars_df <- colnames(tbl)[tolower(colnames(tbl)) %in% tolower(ab_class_vars(ab_class))] + atc_groups <- ab_class_atcgroups(ab_class) + + if (length(vars_df) > 0) { + if (length(result) == 1) { + operator <- " is " + } else { + operator <- " is one of " + } + if (scope == "any") { + scope_txt <- " or " + scope_fn <- any_vars + } else { + scope_txt <- " and " + scope_fn <- all_vars + } + message(blue(paste0("Filtering on ", atc_groups, ": ", scope, " of ", + paste(bold(vars_df), collapse = scope_txt), operator, toString(result)))) + tbl %>% + filter_at(.vars = vars(vars_df), + .vars_predicate = scope_fn(. %in% result), + ...) + } else { + warning(paste0("no antibiotics of class ", atc_groups, " found, leaving data unchanged"), call. = FALSE) + tbl + } +} + +#' @rdname filter_ab_class +#' @export +filter_aminoglycosides <- function(tbl, + result = NULL, + scope = "any", + ...) { + filter_ab_class(tbl = tbl, + ab_class = "aminoglycoside", + result = result, + scope = scope, + ...) +} + +#' @rdname filter_ab_class +#' @export +filter_carbapenems <- function(tbl, + result = NULL, + scope = "any", + ...) { + filter_ab_class(tbl = tbl, + ab_class = "carbapenem", + result = result, + scope = scope, + ...) +} + +#' @rdname filter_ab_class +#' @export +filter_cephalosporins <- function(tbl, + result = NULL, + scope = "any", + ...) { + filter_ab_class(tbl = tbl, + ab_class = "cephalosporin", + result = result, + scope = scope, + ...) +} + +#' @rdname filter_ab_class +#' @export +filter_1st_cephalosporins <- function(tbl, + result = NULL, + scope = "any", + ...) { + filter_ab_class(tbl = tbl, + ab_class = "first-generation cephalosporin", + result = result, + scope = scope, + ...) +} + +#' @rdname filter_ab_class +#' @export +filter_2nd_cephalosporins <- function(tbl, + result = NULL, + scope = "any", + ...) { + filter_ab_class(tbl = tbl, + ab_class = "second-generation cephalosporin", + result = result, + scope = scope, + ...) +} + +#' @rdname filter_ab_class +#' @export +filter_3rd_cephalosporins <- function(tbl, + result = NULL, + scope = "any", + ...) { + filter_ab_class(tbl = tbl, + ab_class = "third-generation cephalosporin", + result = result, + scope = scope, + ...) +} + +#' @rdname filter_ab_class +#' @export +filter_4th_cephalosporins <- function(tbl, + result = NULL, + scope = "any", + ...) { + filter_ab_class(tbl = tbl, + ab_class = "fourth-generation cephalosporin", + result = result, + scope = scope, + ...) +} + +#' @rdname filter_ab_class +#' @export +filter_fluoroquinolones <- function(tbl, + result = NULL, + scope = "any", + ...) { + filter_ab_class(tbl = tbl, + ab_class = "fluoroquinolone", + result = result, + scope = scope, + ...) +} + +#' @rdname filter_ab_class +#' @export +filter_glycopeptides <- function(tbl, + result = NULL, + scope = "any", + ...) { + filter_ab_class(tbl = tbl, + ab_class = "glycopeptide", + result = result, + scope = scope, + ...) +} + +#' @rdname filter_ab_class +#' @export +filter_macrolides <- function(tbl, + result = NULL, + scope = "any", + ...) { + filter_ab_class(tbl = tbl, + ab_class = "macrolide", + result = result, + scope = scope, + ...) +} + +#' @rdname filter_ab_class +#' @export +filter_tetracyclines <- function(tbl, + result = NULL, + scope = "any", + ...) { + filter_ab_class(tbl = tbl, + ab_class = "tetracycline", + result = result, + scope = scope, + ...) +} + +#' @importFrom dplyr %>% filter_at any_vars select +ab_class_vars <- function(ab_class) { + ab_vars <- AMR::antibiotics %>% + filter_at(vars(c("atc_group1", "atc_group2")), any_vars(. %like% ab_class)) %>% + select(atc:trade_name) %>% + as.matrix() %>% + as.character() %>% + paste(collapse = "|") %>% + strsplit("|", fixed = TRUE) %>% + unlist() %>% + unique() + ab_vars[!is.na(ab_vars)] +} + +#' @importFrom dplyr %>% filter pull +ab_class_atcgroups <- function(ab_class) { + AMR::antibiotics %>% + filter(atc %in% ab_class_vars(ab_class)) %>% + pull("atc_group2") %>% + unique() %>% + tolower() %>% + paste(collapse = "/") +} diff --git a/R/mo.R b/R/mo.R index 856f68ba..b15f0268 100755 --- a/R/mo.R +++ b/R/mo.R @@ -174,14 +174,26 @@ as.mo <- function(x, Becker = FALSE, Lancefield = FALSE, allow_uncertain = TRUE, # check onLoad() in R/zzz.R: data tables are created there. } - if (deparse(substitute(reference_df)) == "get_mo_source()" + if (mo_source_isvalid(reference_df) & isFALSE(Becker) & isFALSE(Lancefield) & !is.null(reference_df) - & all(x %in% reference_df[,1])) { + & all(x %in% reference_df[,1][[1]])) { + # has valid own reference_df # (data.table not faster here) + reference_df <- reference_df %>% filter(!is.na(mo)) + # keep only first two columns, second must be mo + if (colnames(reference_df)[1] == "mo") { + reference_df <- reference_df[, c(2, 1)] + } else { + reference_df <- reference_df[, c(1, 2)] + } colnames(reference_df)[1] <- "x" + # remove factors, just keep characters + suppressWarnings( + reference_df[] <- lapply(reference_df, as.character) + ) suppressWarnings( y <- data.frame(x = x, stringsAsFactors = FALSE) %>% left_join(reference_df, by = "x") %>% @@ -277,8 +289,12 @@ exec_as.mo <- function(x, Becker = FALSE, Lancefield = FALSE, # only check the uniques, which is way faster x <- unique(x) # remove empty values (to later fill them in again with NAs) - # ("xxx" is WHONET code for 'no growth') - x <- x[!is.na(x) & !is.null(x) & !identical(x, "") & !identical(x, "xxx")] + # ("xxx" is WHONET code for 'no growth' and "con" is WHONET code for 'contamination') + x <- x[!is.na(x) + & !is.null(x) + & !identical(x, "") + & !identical(x, "xxx") + & !identical(x, "con")] # conversion of old MO codes from v0.5.0 (ITIS) to later versions (Catalogue of Life) if (any(x %like% "^[BFP]_[A-Z]{3,7}") & !all(x %in% microorganisms$mo)) { @@ -292,14 +308,18 @@ exec_as.mo <- function(x, Becker = FALSE, Lancefield = FALSE, # defined df to check for if (!is.null(reference_df)) { - if (!is.data.frame(reference_df) | NCOL(reference_df) < 2) { - stop('`reference_df` must be a data.frame with at least two columns.', call. = FALSE) - } - if (!"mo" %in% colnames(reference_df)) { + if (!mo_source_isvalid(reference_df)) { stop("`reference_df` must contain a column `mo` with values from the 'microorganisms' data set.", call. = FALSE) } reference_df <- reference_df %>% filter(!is.na(mo)) - # # remove factors, just keep characters + # keep only first two columns, second must be mo + if (colnames(reference_df)[1] == "mo") { + reference_df <- reference_df[, c(2, 1)] + } else { + reference_df <- reference_df[, c(1, 2)] + } + colnames(reference_df)[1] <- "x" + # remove factors, just keep characters suppressWarnings( reference_df[] <- lapply(reference_df, as.character) ) @@ -314,8 +334,7 @@ exec_as.mo <- function(x, Becker = FALSE, Lancefield = FALSE, return(rep(NA_character_, length(x_input))) } - } else if (all(x %in% reference_df[, 1]) - & all(reference_df[, "mo"] %in% AMR::microorganisms$mo)) { + } else if (all(x %in% reference_df[, 1][[1]])) { # all in reference df colnames(reference_df)[1] <- "x" suppressWarnings( @@ -420,12 +439,12 @@ exec_as.mo <- function(x, Becker = FALSE, Lancefield = FALSE, next } - if (any(x_trimmed[i] %in% c(NA, ""))) { + if (any(x_trimmed[i] %in% c(NA, "", "xxx", "con"))) { x[i] <- NA_character_ next } - if (tolower(x_trimmed[i]) %in% c("xxx", "other", "none", "unknown")) { + if (tolower(x_trimmed[i]) %in% c("other", "none", "unknown")) { # empty and nonsense values, ignore without warning x[i] <- microorganismsDT[mo == "UNKNOWN", ..property][[1]] next @@ -959,7 +978,11 @@ exec_as.mo <- function(x, Becker = FALSE, Lancefield = FALSE, # Wrap up ---------------------------------------------------------------- # comply to x, which is also unique and without empty values - x_input_unique_nonempty <- unique(x_input[!is.na(x_input) & !is.null(x_input) & !identical(x_input, "") & !identical(x_input, "xxx")]) + x_input_unique_nonempty <- unique(x_input[!is.na(x_input) + & !is.null(x_input) + & !identical(x_input, "") + & !identical(x_input, "xxx") + & !identical(x_input, "con")]) # left join the found results to the original input values (x_input) df_found <- data.frame(input = as.character(x_input_unique_nonempty), diff --git a/R/mo_source.R b/R/mo_source.R index 4a3ae099..34f5f940 100644 --- a/R/mo_source.R +++ b/R/mo_source.R @@ -117,22 +117,6 @@ set_mo_source <- function(path) { stop("File not found: ", path) } - is_valid <- function(df) { - valid <- TRUE - if (!is.data.frame(df)) { - valid <- FALSE - } else if (!"mo" %in% colnames(df)) { - valid <- FALSE - } else if (all(as.data.frame(df)[, 1] == "")) { - valid <- FALSE - } else if (!all(df$mo %in% c("", AMR::microorganisms$mo))) { - valid <- FALSE - } else if (NCOL(df) < 2) { - valid <- FALSE - } - valid - } - if (path %like% '[.]rds$') { df <- readRDS(path) @@ -151,13 +135,13 @@ set_mo_source <- function(path) { try( df <- utils::read.table(header = TRUE, sep = ",", stringsAsFactors = FALSE), silent = TRUE) - if (!is_valid(df)) { + if (!mo_source_isvalid(df)) { # try tab try( df <- utils::read.table(header = TRUE, sep = "\t", stringsAsFactors = FALSE), silent = TRUE) } - if (!is_valid(df)) { + if (!mo_source_isvalid(df)) { # try pipe try( df <- utils::read.table(header = TRUE, sep = "|", stringsAsFactors = FALSE), @@ -165,10 +149,12 @@ set_mo_source <- function(path) { } } - if (!is_valid(df)) { + if (!mo_source_isvalid(df)) { stop("File must contain a column with self-defined values and a reference column `mo` with valid values from the `microorganisms` data set.") } + df <- df %>% filter(!is.na(mo)) + # keep only first two columns, second must be mo if (colnames(df)[1] == "mo") { df <- df[, c(2, 1)] @@ -213,3 +199,22 @@ get_mo_source <- function() { readRDS("~/.mo_source.rds") } + +mo_source_isvalid <- function(x) { + if (deparse(substitute(x)) == "get_mo_source()") { + return(TRUE) + } + if (identical(x, get_mo_source())) { + return(TRUE) + } + if (is.null(x)) { + return(TRUE) + } + if (!is.data.frame(x)) { + return(FALSE) + } + if (!"mo" %in% colnames(x)) { + return(FALSE) + } + all(x$mo %in% c("", AMR::microorganisms$mo)) +} diff --git a/docs/LICENSE-text.html b/docs/LICENSE-text.html index 17b48a67..f4aca6a7 100644 --- a/docs/LICENSE-text.html +++ b/docs/LICENSE-text.html @@ -78,7 +78,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/articles/AMR.html b/docs/articles/AMR.html index ca96704e..e0076c6e 100644 --- a/docs/articles/AMR.html +++ b/docs/articles/AMR.html @@ -40,7 +40,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 @@ -192,7 +192,7 @@

How to conduct AMR analysis

Matthijs S. Berends

-

02 March 2019

+

05 March 2019

@@ -201,7 +201,7 @@ -

Note: values on this page will change with every website update since they are based on randomly created values and the page was written in RMarkdown. However, the methodology remains unchanged. This page was generated on 02 March 2019.

+

Note: values on this page will change with every website update since they are based on randomly created values and the page was written in RMarkdown. However, the methodology remains unchanged. This page was generated on 05 March 2019.

Introduction

@@ -217,21 +217,21 @@ -2019-03-02 +2019-03-05 abcd Escherichia coli S S -2019-03-02 +2019-03-05 abcd Escherichia coli S R -2019-03-02 +2019-03-05 efgh Escherichia coli R @@ -327,30 +327,52 @@ -2012-06-30 +2010-01-23 +E2 +Hospital B +Staphylococcus aureus +I +S +S +S +M + + +2017-12-07 +L8 +Hospital B +Staphylococcus aureus +S +S +S +S +M + + +2012-07-19 W5 Hospital A Staphylococcus aureus S -S +R S S F -2012-07-07 -T4 -Hospital B +2013-11-26 +L7 +Hospital A Escherichia coli -R -R +S +S R S -F +M -2011-02-19 -H3 +2016-01-24 +M7 Hospital B Escherichia coli S @@ -360,37 +382,15 @@ M -2012-12-15 -G10 -Hospital C -Klebsiella pneumoniae -R -S -R -S -M - - -2010-09-11 -L4 -Hospital D -Staphylococcus aureus -S -S -S -S -M - - -2011-03-27 -H5 +2016-11-13 +V10 Hospital A Escherichia coli S S S -R -M +S +F @@ -411,8 +411,8 @@ #> #> Item Count Percent Cum. Count Cum. Percent #> --- ----- ------- -------- ----------- ------------- -#> 1 M 10,433 52.2% 10,433 52.2% -#> 2 F 9,567 47.8% 20,000 100.0% +#> 1 M 10,562 52.8% 10,562 52.8% +#> 2 F 9,438 47.2% 20,000 100.0%

So, we can draw at least two conclusions immediately. From a data scientist perspective, the data looks clean: only values M and F. From a researcher perspective: there are slightly more men. Nothing we didn’t already know.

The data is already quite clean, but we still need to transform some variables. The bacteria column now consists of text, and we want to add more variables based on microbial IDs later on. So, we will transform this column to valid IDs. The mutate() function of the dplyr package makes this really easy:

data <- data %>%
@@ -443,10 +443,10 @@
 #> Kingella kingae (no changes)
 #> 
 #> EUCAST Expert Rules, Intrinsic Resistance and Exceptional Phenotypes (v3.1, 2016)
-#> Table 1:  Intrinsic resistance in Enterobacteriaceae (1323 changes)
+#> Table 1:  Intrinsic resistance in Enterobacteriaceae (1344 changes)
 #> Table 2:  Intrinsic resistance in non-fermentative Gram-negative bacteria (no changes)
 #> Table 3:  Intrinsic resistance in other Gram-negative bacteria (no changes)
-#> Table 4:  Intrinsic resistance in Gram-positive bacteria (2834 changes)
+#> Table 4:  Intrinsic resistance in Gram-positive bacteria (2767 changes)
 #> Table 8:  Interpretive rules for B-lactam agents and Gram-positive cocci (no changes)
 #> Table 9:  Interpretive rules for B-lactam agents and Gram-negative rods (no changes)
 #> Table 10: Interpretive rules for B-lactam agents and other Gram-negative bacteria (no changes)
@@ -462,9 +462,9 @@
 #> Non-EUCAST: piperacillin/tazobactam = S where piperacillin = S (no changes)
 #> Non-EUCAST: trimethoprim/sulfa = S where trimethoprim = S (no changes)
 #> 
-#> => EUCAST rules affected 7,524 out of 20,000 rows
+#> => EUCAST rules affected 7,383 out of 20,000 rows
 #>    -> added 0 test results
-#>    -> changed 4,157 test results (0 to S; 0 to I; 4,157 to R)
+#> -> changed 4,111 test results (0 to S; 0 to I; 4,111 to R)

@@ -489,8 +489,8 @@ #> NOTE: Using column `bacteria` as input for `col_mo`. #> NOTE: Using column `date` as input for `col_date`. #> NOTE: Using column `patient_id` as input for `col_patient_id`. -#> => Found 5,698 first isolates (28.5% of total)

-

So only 28.5% is suitable for resistance analysis! We can now filter on it with the filter() function, also from the dplyr package:

+#> => Found 5,676 first isolates (28.4% of total) +

So only 28.4% is suitable for resistance analysis! We can now filter on it with the filter() function, also from the dplyr package:

data_1st <- data %>% 
   filter(first == TRUE)

For future use, the above two syntaxes can be shortened with the filter_first_isolate() function:

@@ -516,21 +516,21 @@ 1 -2010-01-18 -C7 +2010-01-20 +L10 B_ESCHR_COL -S -S +I +R S S TRUE 2 -2010-02-27 -C7 +2010-03-26 +L10 B_ESCHR_COL -S +R S S S @@ -538,8 +538,8 @@ 3 -2010-04-22 -C7 +2010-05-05 +L10 B_ESCHR_COL S S @@ -549,8 +549,8 @@ 4 -2010-06-09 -C7 +2010-06-20 +L10 B_ESCHR_COL S S @@ -560,19 +560,19 @@ 5 -2011-04-13 -C7 +2010-07-10 +L10 B_ESCHR_COL -R S S S -TRUE +S +FALSE 6 -2011-04-25 -C7 +2010-08-01 +L10 B_ESCHR_COL S S @@ -582,32 +582,32 @@ 7 -2011-08-02 -C7 +2010-08-27 +L10 B_ESCHR_COL R S -R +S S FALSE 8 -2011-10-19 -C7 +2010-09-09 +L10 B_ESCHR_COL R -I +S S S FALSE 9 -2011-10-23 -C7 +2010-09-26 +L10 B_ESCHR_COL -S +R S S S @@ -615,18 +615,18 @@ 10 -2011-11-10 -C7 +2010-10-11 +L10 B_ESCHR_COL -S -S R S +S +S FALSE -

Only 2 isolates are marked as ‘first’ according to CLSI guideline. But when reviewing the antibiogram, it is obvious that some isolates are absolutely different strains and should be included too. This is why we weigh isolates, based on their antibiogram. The key_antibiotics() function adds a vector with 18 key antibiotics: 6 broad spectrum ones, 6 small spectrum for Gram negatives and 6 small spectrum for Gram positives. These can be defined by the user.

+

Only 1 isolates are marked as ‘first’ according to CLSI guideline. But when reviewing the antibiogram, it is obvious that some isolates are absolutely different strains and should be included too. This is why we weigh isolates, based on their antibiogram. The key_antibiotics() function adds a vector with 18 key antibiotics: 6 broad spectrum ones, 6 small spectrum for Gram negatives and 6 small spectrum for Gram positives. These can be defined by the user.

If a column exists with a name like ‘key(…)ab’ the first_isolate() function will automatically use it and determine the first weighted isolates. Mind the NOTEs in below output:

data <- data %>% 
   mutate(keyab = key_antibiotics(.)) %>% 
@@ -637,7 +637,7 @@
 #> NOTE: Using column `patient_id` as input for `col_patient_id`.
 #> NOTE: Using column `keyab` as input for `col_keyantibiotics`. Use col_keyantibiotics  = FALSE to prevent this.
 #> [Criterion] Inclusion based on key antibiotics, ignoring I.
-#> => Found 15,826 first weighted isolates (79.1% of total)
+#> => Found 15,767 first weighted isolates (78.8% of total) @@ -654,11 +654,11 @@ - - + + - - + + @@ -666,32 +666,32 @@ - - + + - + - + - - + + - + - - + + @@ -702,83 +702,83 @@ - - - - - - - - - - - - - - + + - + + + + + + + + + + + + + - - + + - + - - + + - + - + - - + + - + - + - - + + - - + + + -
isolate
12010-01-18C72010-01-20L10 B_ESCHR_COLSSIR S S TRUE
22010-02-27C72010-03-26L10 B_ESCHR_COLSR S S S FALSEFALSETRUE
32010-04-22C72010-05-05L10 B_ESCHR_COL S S S S FALSEFALSETRUE
42010-06-09C72010-06-20L10 B_ESCHR_COL S S
52011-04-13C7B_ESCHR_COLRSSSTRUETRUE
62011-04-25C72010-07-10L10 B_ESCHR_COL S S S S FALSETRUEFALSE
62010-08-01L10B_ESCHR_COLSSSSFALSEFALSE
72011-08-02C72010-08-27L10 B_ESCHR_COL R SRS S FALSE TRUE
82011-10-19C72010-09-09L10 B_ESCHR_COL RIS S S FALSETRUEFALSE
92011-10-23C72010-09-26L10 B_ESCHR_COLSR S S S FALSETRUEFALSE
102011-11-10C72010-10-11L10 B_ESCHR_COLSS R SSSFALSE FALSETRUE
-

Instead of 2, now 7 isolates are flagged. In total, 79.1% of all isolates are marked ‘first weighted’ - 50.6% more than when using the CLSI guideline. In real life, this novel algorithm will yield 5-10% more isolates than the classic CLSI guideline.

+

Instead of 1, now 4 isolates are flagged. In total, 78.8% of all isolates are marked ‘first weighted’ - 50.5% more than when using the CLSI guideline. In real life, this novel algorithm will yield 5-10% more isolates than the classic CLSI guideline.

As with filter_first_isolate(), there’s a shortcut for this new algorithm too:

data_1st <- data %>% 
   filter_first_weighted_isolate()
-

So we end up with 15,826 isolates for analysis.

+

So we end up with 15,767 isolates for analysis.

We can remove unneeded columns:

data_1st <- data_1st %>% 
   select(-c(first, keyab))
@@ -786,7 +786,6 @@
head(data_1st)
- @@ -803,79 +802,44 @@ - - - + + - - - - + + - - - - + + + + + + - - - + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + - + + @@ -883,12 +847,41 @@ - - - + + + + + + + + + + + + + + + + + - + + + + + + + + + + + + + + + + @@ -915,9 +908,9 @@
freq(paste(data_1st$genus, data_1st$species))

Or can be used like the dplyr way, which is easier readable:

data_1st %>% freq(genus, species)
-

Frequency table of genus and species from a data.frame (15,826 x 13)

+

Frequency table of genus and species from a data.frame (15,767 x 13)

Columns: 2
-Length: 15,826 (of which NA: 0 = 0.00%)
+Length: 15,767 (of which NA: 0 = 0.00%)
Unique: 4

Shortest: 16
Longest: 24

@@ -934,33 +927,33 @@ Longest: 24

- - - - + + + + - - - - + + + + - - - - + + + + - - - + + + @@ -971,7 +964,7 @@ Longest: 24

Resistance percentages

The functions portion_R(), portion_RI(), portion_I(), portion_IS() and portion_S() can be used to determine the portion of a specific antimicrobial outcome. They can be used on their own:

data_1st %>% portion_IR(amox)
-#> [1] 0.4830027
+#> [1] 0.4762479

Or can be used in conjuction with group_by() and summarise(), both from the dplyr package:

data_1st %>% 
   group_by(hospital) %>% 
@@ -984,19 +977,19 @@ Longest: 24

- + - + - + - +
date patient_id hospital
22012-07-07T42010-01-23E2 Hospital BB_ESCHR_COLRRRB_STPHY_AURI SFGram negativeEscherichiacoliSSMGram positiveStaphylococcusaureus TRUE
32011-02-19H32017-12-07L8 Hospital BB_ESCHR_COLSSSSMGram negativeEscherichiacoliTRUE
42012-12-15G10Hospital CB_KLBSL_PNERSRSMGram negativeKlebsiellapneumoniaeTRUE
62011-03-27H5Hospital AB_ESCHR_COLSSSRMGram negativeEscherichiacoliTRUE
72012-06-22Q8Hospital A B_STPHY_AUR S SSSMGram positiveStaphylococcusaureusTRUE
2012-07-19W5Hospital AB_STPHY_AURS RRSS F Gram positive StaphylococcusTRUE
82015-06-27Q22013-11-26L7Hospital AB_ESCHR_COLSSRSMGram negativeEscherichiacoliTRUE
2016-01-24M7 Hospital B B_ESCHR_COLRSSSSMGram negativeEscherichiacoliTRUE
2016-11-13V10Hospital AB_ESCHR_COLS S S S
1 Escherichia coli7,71448.7%7,71448.7%7,76249.2%7,76249.2%
2 Staphylococcus aureus3,97725.1%11,69173.9%4,01425.5%11,77674.7%
3 Streptococcus pneumoniae2,51415.9%14,20589.8%2,45015.5%14,22690.2%
4 Klebsiella pneumoniae1,62110.2%15,8261,5419.8%15,767 100.0%
Hospital A0.47988200.4717496
Hospital B0.47928350.4754662
Hospital C0.48637140.4748170
Hospital D0.49157300.4854430
@@ -1014,23 +1007,23 @@ Longest: 24

Hospital A -0.4798820 -4747 +0.4717496 +4761 Hospital B -0.4792835 -5527 +0.4754662 +5523 Hospital C -0.4863714 -2348 +0.4748170 +2323 Hospital D -0.4915730 -3204 +0.4854430 +3160 @@ -1050,27 +1043,27 @@ Longest: 24

Escherichia -0.7313975 -0.8940887 -0.9752398 +0.7333162 +0.9035043 +0.9748776 Klebsiella -0.7143738 -0.8994448 -0.9697717 +0.7352369 +0.9104478 +0.9733939 Staphylococcus -0.7301986 -0.9104853 -0.9786271 +0.7416542 +0.9160438 +0.9763328 Streptococcus -0.7430390 +0.7473469 0.0000000 -0.7430390 +0.7473469 diff --git a/docs/articles/AMR_files/figure-html/plot 1-1.png b/docs/articles/AMR_files/figure-html/plot 1-1.png index e7062639..49a734cc 100644 Binary files a/docs/articles/AMR_files/figure-html/plot 1-1.png and b/docs/articles/AMR_files/figure-html/plot 1-1.png differ diff --git a/docs/articles/AMR_files/figure-html/plot 3-1.png b/docs/articles/AMR_files/figure-html/plot 3-1.png index 80467329..babc025c 100644 Binary files a/docs/articles/AMR_files/figure-html/plot 3-1.png and b/docs/articles/AMR_files/figure-html/plot 3-1.png differ diff --git a/docs/articles/AMR_files/figure-html/plot 4-1.png b/docs/articles/AMR_files/figure-html/plot 4-1.png index cf9112de..4ec461ef 100644 Binary files a/docs/articles/AMR_files/figure-html/plot 4-1.png and b/docs/articles/AMR_files/figure-html/plot 4-1.png differ diff --git a/docs/articles/AMR_files/figure-html/plot 5-1.png b/docs/articles/AMR_files/figure-html/plot 5-1.png index 7149c905..47ed2dd4 100644 Binary files a/docs/articles/AMR_files/figure-html/plot 5-1.png and b/docs/articles/AMR_files/figure-html/plot 5-1.png differ diff --git a/docs/articles/EUCAST.html b/docs/articles/EUCAST.html index 5a814a68..ceb9fd3f 100644 --- a/docs/articles/EUCAST.html +++ b/docs/articles/EUCAST.html @@ -40,7 +40,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 @@ -192,7 +192,7 @@

How to apply EUCAST rules

Matthijs S. Berends

-

02 March 2019

+

05 March 2019

diff --git a/docs/articles/G_test.html b/docs/articles/G_test.html index e44668d0..f25feb89 100644 --- a/docs/articles/G_test.html +++ b/docs/articles/G_test.html @@ -40,7 +40,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 @@ -192,7 +192,7 @@

How to use the G-test

Matthijs S. Berends

-

02 March 2019

+

05 March 2019

diff --git a/docs/articles/SPSS.html b/docs/articles/SPSS.html index 751ad91b..a7ee28a7 100644 --- a/docs/articles/SPSS.html +++ b/docs/articles/SPSS.html @@ -40,7 +40,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/articles/WHONET.html b/docs/articles/WHONET.html index 574b0cd2..c6d941c0 100644 --- a/docs/articles/WHONET.html +++ b/docs/articles/WHONET.html @@ -40,7 +40,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 @@ -192,7 +192,7 @@

How to work with WHONET data

Matthijs S. Berends

-

02 March 2019

+

05 March 2019

diff --git a/docs/articles/atc_property.html b/docs/articles/atc_property.html index ab0fa610..f541d6cf 100644 --- a/docs/articles/atc_property.html +++ b/docs/articles/atc_property.html @@ -40,7 +40,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 @@ -192,7 +192,7 @@

How to get properties of an antibiotic

Matthijs S. Berends

-

02 March 2019

+

05 March 2019

diff --git a/docs/articles/benchmarks.html b/docs/articles/benchmarks.html index e65cf80c..d89b9b9c 100644 --- a/docs/articles/benchmarks.html +++ b/docs/articles/benchmarks.html @@ -40,7 +40,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 @@ -192,7 +192,7 @@

Benchmarks

Matthijs S. Berends

-

02 March 2019

+

05 March 2019

@@ -217,14 +217,14 @@ times = 10) print(S.aureus, unit = "ms", signif = 3) #> Unit: milliseconds -#> expr min lq mean median uq max neval -#> as.mo("sau") 16.60 16.70 16.90 16.70 16.80 18.20 10 -#> as.mo("stau") 31.80 32.00 44.30 32.10 72.40 73.60 10 -#> as.mo("staaur") 16.70 16.70 16.80 16.70 16.80 17.30 10 -#> as.mo("STAAUR") 16.70 16.80 35.20 18.60 58.00 73.00 10 -#> as.mo("S. aureus") 24.60 24.60 33.50 24.70 24.90 68.70 10 -#> as.mo("S. aureus") 24.50 24.70 25.30 24.90 26.00 26.40 10 -#> as.mo("Staphylococcus aureus") 7.35 7.45 7.53 7.51 7.56 7.97 10
+#> expr min lq mean median uq max neval +#> as.mo("sau") 16.80 17.20 25.80 18.10 32.10 52.8 10 +#> as.mo("stau") 32.20 33.10 43.30 34.00 42.40 82.3 10 +#> as.mo("staaur") 16.70 16.80 25.40 17.20 19.80 60.4 10 +#> as.mo("STAAUR") 16.70 16.80 22.40 17.90 20.20 61.7 10 +#> as.mo("S. aureus") 24.90 25.10 42.00 26.20 67.50 88.8 10 +#> as.mo("S. aureus") 24.50 25.00 43.70 25.30 67.90 78.2 10 +#> as.mo("Staphylococcus aureus") 7.47 7.48 9.63 7.53 7.69 28.3 10

In the table above, all measurements are shown in milliseconds (thousands of seconds). A value of 5 milliseconds means it can determine 200 input values per second. It case of 100 milliseconds, this is only 10 input values per second. The second input is the only one that has to be looked up thoroughly. All the others are known codes (the first one is a WHONET code) or common laboratory codes, or common full organism names like the last one. Full organism names are always preferred.

To achieve this speed, the as.mo function also takes into account the prevalence of human pathogenic microorganisms. The downside is of course that less prevalent microorganisms will be determined less fast. See this example for the ID of Thermus islandicus (B_THERMS_ISL), a bug probably never found before in humans:

T.islandicus <- microbenchmark(as.mo("theisl"),
@@ -235,13 +235,13 @@
                                  times = 10)
 print(T.islandicus, unit = "ms", signif = 3)
 #> Unit: milliseconds
-#>                         expr   min    lq  mean median  uq max neval
-#>              as.mo("theisl") 265.0 268.0 294.0  307.0 312 321    10
-#>              as.mo("THEISL") 264.0 264.0 312.0  307.0 316 464    10
-#>       as.mo("T. islandicus") 142.0 142.0 159.0  143.0 187 216    10
-#>      as.mo("T.  islandicus") 142.0 143.0 173.0  185.0 187 190    10
-#>  as.mo("Thermus islandicus")  68.1  68.4  81.9   68.6 111 115    10
-

That takes 8 times as much time on average. A value of 100 milliseconds means it can only determine ~10 different input values per second. We can conclude that looking up arbitrary codes of less prevalent microorganisms is the worst way to go, in terms of calculation performance. Full names (like Thermus islandicus) are almost fast - these are the most probable input from most data sets.

+#> expr min lq mean median uq max neval +#> as.mo("theisl") 275.0 304.0 310 309.0 316 337 10 +#> as.mo("THEISL") 263.0 304.0 311 306.0 312 391 10 +#> as.mo("T. islandicus") 142.0 143.0 168 148.0 188 220 10 +#> as.mo("T. islandicus") 142.0 142.0 169 143.0 185 312 10 +#> as.mo("Thermus islandicus") 68.1 68.6 101 89.8 122 179 10 +

That takes 7 times as much time on average. A value of 100 milliseconds means it can only determine ~10 different input values per second. We can conclude that looking up arbitrary codes of less prevalent microorganisms is the worst way to go, in terms of calculation performance. Full names (like Thermus islandicus) are almost fast - these are the most probable input from most data sets.

In the figure below, we compare Escherichia coli (which is very common) with Prevotella brevis (which is moderately common) and with Thermus islandicus (which is very uncommon):

par(mar = c(5, 16, 4, 2)) # set more space for left margin text (16)
 
@@ -286,9 +286,9 @@
                          times = 10)
 print(run_it, unit = "ms", signif = 3)
 #> Unit: milliseconds
-#>            expr min  lq mean median  uq  max neval
-#>  mo_fullname(x) 732 772  823    819 858 1020    10
-

So transforming 500,000 values (!!) of 50 unique values only takes 0.82 seconds (819 ms). You only lose time on your unique input values.

+#> expr min lq mean median uq max neval +#> mo_fullname(x) 687 738 767 770 774 887 10 +

So transforming 500,000 values (!!) of 50 unique values only takes 0.77 seconds (770 ms). You only lose time on your unique input values.

@@ -300,10 +300,10 @@ times = 10) print(run_it, unit = "ms", signif = 3) #> Unit: milliseconds -#> expr min lq mean median uq max neval -#> A 11.100 11.400 16.700 11.700 14.400 43.200 10 -#> B 22.300 22.400 22.800 22.700 22.900 24.100 10 -#> C 0.324 0.439 0.532 0.577 0.582 0.677 10

+#> expr min lq mean median uq max neval +#> A 11.100 11.300 15.600 11.400 11.600 53.4 10 +#> B 22.200 22.500 22.800 22.800 23.000 23.7 10 +#> C 0.322 0.326 0.518 0.563 0.578 0.8 10

So going from mo_fullname("Staphylococcus aureus") to "Staphylococcus aureus" takes 0.0006 seconds - it doesn’t even start calculating if the result would be the same as the expected resulting value. That goes for all helper functions:

run_it <- microbenchmark(A = mo_species("aureus"),
                          B = mo_genus("Staphylococcus"),
@@ -317,14 +317,14 @@
 print(run_it, unit = "ms", signif = 3)
 #> Unit: milliseconds
 #>  expr   min    lq  mean median    uq   max neval
-#>     A 0.322 0.338 0.397  0.384 0.415 0.569    10
-#>     B 0.316 0.370 0.442  0.442 0.508 0.601    10
-#>     C 0.335 0.385 0.502  0.504 0.566 0.724    10
-#>     D 0.283 0.324 0.362  0.366 0.389 0.437    10
-#>     E 0.252 0.274 0.317  0.323 0.355 0.383    10
-#>     F 0.255 0.275 0.325  0.332 0.348 0.411    10
-#>     G 0.259 0.272 0.307  0.299 0.318 0.412    10
-#>     H 0.271 0.319 0.338  0.334 0.362 0.418    10
+#> A 0.330 0.345 0.421 0.441 0.461 0.525 10 +#> B 0.355 0.378 0.453 0.435 0.464 0.754 10 +#> C 0.315 0.374 0.506 0.516 0.633 0.700 10 +#> D 0.273 0.329 0.353 0.365 0.385 0.391 10 +#> E 0.279 0.322 0.330 0.335 0.343 0.366 10 +#> F 0.247 0.263 0.315 0.319 0.355 0.429 10 +#> G 0.276 0.320 0.342 0.328 0.371 0.447 10 +#> H 0.251 0.258 0.315 0.329 0.360 0.368 10

Of course, when running mo_phylum("Firmicutes") the function has zero knowledge about the actual microorganism, namely S. aureus. But since the result would be "Firmicutes" too, there is no point in calculating the result. And because this package ‘knows’ all phyla of all known bacteria (according to the Catalogue of Life), it can just return the initial value immediately.

@@ -351,13 +351,13 @@ print(run_it, unit = "ms", signif = 4) #> Unit: milliseconds #> expr min lq mean median uq max neval -#> en 14.92 15.11 15.44 15.31 15.83 16.30 10 -#> de 27.88 27.89 32.32 28.03 28.37 69.82 10 -#> nl 27.39 28.01 40.70 28.48 69.20 70.26 10 -#> es 27.69 27.93 38.06 28.12 29.21 84.95 10 -#> it 27.73 27.95 28.16 28.00 28.15 29.40 10 -#> fr 27.13 27.65 32.76 28.41 29.50 69.48 10 -#> pt 27.08 27.34 27.89 27.99 28.05 29.40 10
+#> en 14.98 15.35 19.58 15.51 15.58 56.78 10 +#> de 27.26 27.69 28.05 27.85 28.01 29.44 10 +#> nl 27.07 27.73 31.89 27.87 28.00 69.50 10 +#> es 26.98 27.43 31.98 27.84 28.09 69.30 10 +#> it 27.26 27.57 28.38 27.82 28.92 32.14 10 +#> fr 27.21 27.72 36.16 27.83 28.19 70.08 10 +#> pt 27.21 27.78 36.17 27.96 28.54 69.43 10

Currently supported are German, Dutch, Spanish, Italian, French and Portuguese.

diff --git a/docs/articles/benchmarks_files/figure-html/unnamed-chunk-5-1.png b/docs/articles/benchmarks_files/figure-html/unnamed-chunk-5-1.png index 558d400a..12367582 100644 Binary files a/docs/articles/benchmarks_files/figure-html/unnamed-chunk-5-1.png and b/docs/articles/benchmarks_files/figure-html/unnamed-chunk-5-1.png differ diff --git a/docs/articles/freq.html b/docs/articles/freq.html index 3fe5d762..9aa22ce2 100644 --- a/docs/articles/freq.html +++ b/docs/articles/freq.html @@ -40,7 +40,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 @@ -192,7 +192,7 @@

How to create frequency tables

Matthijs S. Berends

-

02 March 2019

+

05 March 2019

diff --git a/docs/articles/index.html b/docs/articles/index.html index 8a3a33cb..d4d7734d 100644 --- a/docs/articles/index.html +++ b/docs/articles/index.html @@ -78,7 +78,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/articles/mo_property.html b/docs/articles/mo_property.html index 8e0ffa73..e61fca60 100644 --- a/docs/articles/mo_property.html +++ b/docs/articles/mo_property.html @@ -40,7 +40,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 @@ -192,7 +192,7 @@

How to get properties of a microorganism

Matthijs S. Berends

-

02 March 2019

+

05 March 2019

diff --git a/docs/articles/resistance_predict.html b/docs/articles/resistance_predict.html index 17450ab0..7fd8803d 100644 --- a/docs/articles/resistance_predict.html +++ b/docs/articles/resistance_predict.html @@ -40,7 +40,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 @@ -192,7 +192,7 @@

How to predict antimicrobial resistance

Matthijs S. Berends

-

02 March 2019

+

05 March 2019

diff --git a/docs/authors.html b/docs/authors.html index b68c9c3d..6c9d4a73 100644 --- a/docs/authors.html +++ b/docs/authors.html @@ -78,7 +78,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/index.html b/docs/index.html index 145331be..9a7bfa51 100644 --- a/docs/index.html +++ b/docs/index.html @@ -42,7 +42,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/news/index.html b/docs/news/index.html index feff6917..635a33e1 100644 --- a/docs/news/index.html +++ b/docs/news/index.html @@ -78,7 +78,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/AMR-deprecated.html b/docs/reference/AMR-deprecated.html index a1b048db..ef457f09 100644 --- a/docs/reference/AMR-deprecated.html +++ b/docs/reference/AMR-deprecated.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/AMR.html b/docs/reference/AMR.html index 617f2556..e5756947 100644 --- a/docs/reference/AMR.html +++ b/docs/reference/AMR.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/WHOCC.html b/docs/reference/WHOCC.html index 59a38ca1..469ec5cc 100644 --- a/docs/reference/WHOCC.html +++ b/docs/reference/WHOCC.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/WHONET.html b/docs/reference/WHONET.html index a82e7592..4b83ea0f 100644 --- a/docs/reference/WHONET.html +++ b/docs/reference/WHONET.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/abname.html b/docs/reference/abname.html index 7e597412..2d4d4541 100644 --- a/docs/reference/abname.html +++ b/docs/reference/abname.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/age.html b/docs/reference/age.html index a427f2d0..27c423ea 100644 --- a/docs/reference/age.html +++ b/docs/reference/age.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/age_groups.html b/docs/reference/age_groups.html index ac81bc1c..61f3a71c 100644 --- a/docs/reference/age_groups.html +++ b/docs/reference/age_groups.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/antibiotics.html b/docs/reference/antibiotics.html index f04b89ae..e8331f7e 100644 --- a/docs/reference/antibiotics.html +++ b/docs/reference/antibiotics.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/as.atc.html b/docs/reference/as.atc.html index 4055d3ae..7b51bce7 100644 --- a/docs/reference/as.atc.html +++ b/docs/reference/as.atc.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/as.mic.html b/docs/reference/as.mic.html index e55c6e5b..09ee45cb 100644 --- a/docs/reference/as.mic.html +++ b/docs/reference/as.mic.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/as.mo.html b/docs/reference/as.mo.html index 05112dc8..9f360adc 100644 --- a/docs/reference/as.mo.html +++ b/docs/reference/as.mo.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/as.rsi.html b/docs/reference/as.rsi.html index 5767538f..4e4320e4 100644 --- a/docs/reference/as.rsi.html +++ b/docs/reference/as.rsi.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/atc_online.html b/docs/reference/atc_online.html index b001f3bf..1cdf7017 100644 --- a/docs/reference/atc_online.html +++ b/docs/reference/atc_online.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/atc_property.html b/docs/reference/atc_property.html index 4be7e9f6..6f1f657c 100644 --- a/docs/reference/atc_property.html +++ b/docs/reference/atc_property.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/availability.html b/docs/reference/availability.html index c949609e..4adaa29e 100644 --- a/docs/reference/availability.html +++ b/docs/reference/availability.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/catalogue_of_life.html b/docs/reference/catalogue_of_life.html index 4c4a6fea..106cac8a 100644 --- a/docs/reference/catalogue_of_life.html +++ b/docs/reference/catalogue_of_life.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/catalogue_of_life_version.html b/docs/reference/catalogue_of_life_version.html index 34f8cf1f..0ec25959 100644 --- a/docs/reference/catalogue_of_life_version.html +++ b/docs/reference/catalogue_of_life_version.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/count.html b/docs/reference/count.html index 2720479f..1522f185 100644 --- a/docs/reference/count.html +++ b/docs/reference/count.html @@ -81,7 +81,7 @@ count_R and count_IR can be used to count resistant isolates, count_S and count_ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/eucast_rules.html b/docs/reference/eucast_rules.html index d76a1404..7ed4caff 100644 --- a/docs/reference/eucast_rules.html +++ b/docs/reference/eucast_rules.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/filter_ab_class.html b/docs/reference/filter_ab_class.html new file mode 100644 index 00000000..e9eff8a9 --- /dev/null +++ b/docs/reference/filter_ab_class.html @@ -0,0 +1,369 @@ + + + + + + + + +Filter on antibiotic class — filter_ab_class • AMR (for R) + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
+
+ + + +
+ +
+
+ + +
+ +

Filter on specific antibiotic variables based on their class (ATC groups).

+ +
+ +
filter_ab_class(tbl, ab_class, result = NULL, scope = "any", ...)
+
+filter_aminoglycosides(tbl, result = NULL, scope = "any", ...)
+
+filter_carbapenems(tbl, result = NULL, scope = "any", ...)
+
+filter_cephalosporins(tbl, result = NULL, scope = "any", ...)
+
+filter_1st_cephalosporins(tbl, result = NULL, scope = "any", ...)
+
+filter_2nd_cephalosporins(tbl, result = NULL, scope = "any", ...)
+
+filter_3rd_cephalosporins(tbl, result = NULL, scope = "any", ...)
+
+filter_4th_cephalosporins(tbl, result = NULL, scope = "any", ...)
+
+filter_fluoroquinolones(tbl, result = NULL, scope = "any", ...)
+
+filter_glycopeptides(tbl, result = NULL, scope = "any", ...)
+
+filter_macrolides(tbl, result = NULL, scope = "any", ...)
+
+filter_tetracyclines(tbl, result = NULL, scope = "any", ...)
+ +

Arguments

+ + + + + + + + + + + + + + + + + + + + + + +
tbl

a data set

ab_class

an antimicrobial class, like "carbapenems"

result

an antibiotic result: S, I or R (or a combination of more of them)

scope

the scope to check which variables to check, can be "any" (default) or "all"

...

parameters passed on to filter_at

+ +

Details

+ +

The antibiotics data set will be searched for ab_class in the columns atc_group1 and atc_group2 (case-insensitive). Next, tbl will be checked for column names with a value in any abbreviations, codes or official names found in the antibiotics data set.

+ + +

Examples

+
# NOT RUN {
+library(dplyr)
+
+# filter on isolates that have any result for any aminoglycoside
+septic_patients %>% filter_aminoglycosides()
+
+# this is essentially the same as:
+septic_patients %>%
+  filter_at(.vars = vars(c("gent", "tobr", "amik", "kana")),
+            .vars_predicate = any_vars(. %in% c("S", "I", "R")))
+
+
+# filter on isolates that show resistance to ANY aminoglycoside
+septic_patients %>% filter_aminoglycosides("R")
+
+# filter on isolates that show resistance to ALL aminoglycosides
+septic_patients %>% filter_aminoglycosides("R", "all")
+
+# filter on isolates that show resistance to
+# any aminoglycoside and any fluoroquinolone
+septic_patients %>%
+  filter_aminoglycosides("R", "any") %>%
+  filter_fluoroquinolones("R", "any")
+# }
+
+ +
+ + +
+ + + + + + + + + diff --git a/docs/reference/first_isolate.html b/docs/reference/first_isolate.html index 69620280..78a90366 100644 --- a/docs/reference/first_isolate.html +++ b/docs/reference/first_isolate.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/freq.html b/docs/reference/freq.html index db6130c2..f1c01f6e 100644 --- a/docs/reference/freq.html +++ b/docs/reference/freq.html @@ -81,7 +81,7 @@ top_freq can be used to get the top/bottom n items of a frequency table, with co AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/g.test.html b/docs/reference/g.test.html index 35987628..c951f39b 100644 --- a/docs/reference/g.test.html +++ b/docs/reference/g.test.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/get_locale.html b/docs/reference/get_locale.html index 037f6490..33cf12ff 100644 --- a/docs/reference/get_locale.html +++ b/docs/reference/get_locale.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/ggplot_rsi.html b/docs/reference/ggplot_rsi.html index ea2f27ea..b5436028 100644 --- a/docs/reference/ggplot_rsi.html +++ b/docs/reference/ggplot_rsi.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/guess_ab_col.html b/docs/reference/guess_ab_col.html index 8d8768e9..10cc5930 100644 --- a/docs/reference/guess_ab_col.html +++ b/docs/reference/guess_ab_col.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/index.html b/docs/reference/index.html index 2211a837..64624283 100644 --- a/docs/reference/index.html +++ b/docs/reference/index.html @@ -78,7 +78,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/join.html b/docs/reference/join.html index 5b9a9103..8497c7b3 100644 --- a/docs/reference/join.html +++ b/docs/reference/join.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/key_antibiotics.html b/docs/reference/key_antibiotics.html index 8cf0479f..55e1d88b 100644 --- a/docs/reference/key_antibiotics.html +++ b/docs/reference/key_antibiotics.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/kurtosis.html b/docs/reference/kurtosis.html index 24eb0a1d..ac0a855b 100644 --- a/docs/reference/kurtosis.html +++ b/docs/reference/kurtosis.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/like.html b/docs/reference/like.html index 606312c1..1b0b35c4 100644 --- a/docs/reference/like.html +++ b/docs/reference/like.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/mdro.html b/docs/reference/mdro.html index bc8cbfea..f0b447a7 100644 --- a/docs/reference/mdro.html +++ b/docs/reference/mdro.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/microorganisms.codes.html b/docs/reference/microorganisms.codes.html index dc56e096..104b3c0c 100644 --- a/docs/reference/microorganisms.codes.html +++ b/docs/reference/microorganisms.codes.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/microorganisms.html b/docs/reference/microorganisms.html index 9d3eff77..60da982c 100644 --- a/docs/reference/microorganisms.html +++ b/docs/reference/microorganisms.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/microorganisms.old.html b/docs/reference/microorganisms.old.html index 21bf39a0..75b08ab1 100644 --- a/docs/reference/microorganisms.old.html +++ b/docs/reference/microorganisms.old.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/mo_property.html b/docs/reference/mo_property.html index 376877ac..46f508c6 100644 --- a/docs/reference/mo_property.html +++ b/docs/reference/mo_property.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/mo_source.html b/docs/reference/mo_source.html index e2d9c6bf..5e1f7a73 100644 --- a/docs/reference/mo_source.html +++ b/docs/reference/mo_source.html @@ -81,7 +81,7 @@ This is the fastest way to have your organisation (or analysis) specific codes p AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/p.symbol.html b/docs/reference/p.symbol.html index bd572dcb..b8c8487f 100644 --- a/docs/reference/p.symbol.html +++ b/docs/reference/p.symbol.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/portion.html b/docs/reference/portion.html index bdfe1066..1fdc04c7 100644 --- a/docs/reference/portion.html +++ b/docs/reference/portion.html @@ -81,7 +81,7 @@ portion_R and portion_IR can be used to calculate resistance, portion_S and port AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/read.4D.html b/docs/reference/read.4D.html index d77a0b46..5dbdb540 100644 --- a/docs/reference/read.4D.html +++ b/docs/reference/read.4D.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/resistance_predict.html b/docs/reference/resistance_predict.html index 2dc70e28..2c1d01d2 100644 --- a/docs/reference/resistance_predict.html +++ b/docs/reference/resistance_predict.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/rsi.html b/docs/reference/rsi.html index ff3d0437..b1636405 100644 --- a/docs/reference/rsi.html +++ b/docs/reference/rsi.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/septic_patients.html b/docs/reference/septic_patients.html index 53e04a86..0857c77a 100644 --- a/docs/reference/septic_patients.html +++ b/docs/reference/septic_patients.html @@ -80,7 +80,7 @@ AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/reference/skewness.html b/docs/reference/skewness.html index 32a53957..be577631 100644 --- a/docs/reference/skewness.html +++ b/docs/reference/skewness.html @@ -81,7 +81,7 @@ When negative: the left tail is longer; the mass of the distribution is concentr AMR (for R) - 0.5.0.9020 + 0.5.0.9021 diff --git a/docs/sitemap.xml b/docs/sitemap.xml index b84f5b87..d641d618 100644 --- a/docs/sitemap.xml +++ b/docs/sitemap.xml @@ -60,6 +60,9 @@ https://msberends.gitlab.io/AMR/reference/eucast_rules.html + + https://msberends.gitlab.io/AMR/reference/filter_ab_class.html + https://msberends.gitlab.io/AMR/reference/first_isolate.html diff --git a/man/filter_ab_class.Rd b/man/filter_ab_class.Rd new file mode 100644 index 00000000..c81d16e9 --- /dev/null +++ b/man/filter_ab_class.Rd @@ -0,0 +1,82 @@ +% Generated by roxygen2: do not edit by hand +% Please edit documentation in R/filter_ab_class.R +\name{filter_ab_class} +\alias{filter_ab_class} +\alias{filter_aminoglycosides} +\alias{filter_carbapenems} +\alias{filter_cephalosporins} +\alias{filter_1st_cephalosporins} +\alias{filter_2nd_cephalosporins} +\alias{filter_3rd_cephalosporins} +\alias{filter_4th_cephalosporins} +\alias{filter_fluoroquinolones} +\alias{filter_glycopeptides} +\alias{filter_macrolides} +\alias{filter_tetracyclines} +\title{Filter on antibiotic class} +\usage{ +filter_ab_class(tbl, ab_class, result = NULL, scope = "any", ...) + +filter_aminoglycosides(tbl, result = NULL, scope = "any", ...) + +filter_carbapenems(tbl, result = NULL, scope = "any", ...) + +filter_cephalosporins(tbl, result = NULL, scope = "any", ...) + +filter_1st_cephalosporins(tbl, result = NULL, scope = "any", ...) + +filter_2nd_cephalosporins(tbl, result = NULL, scope = "any", ...) + +filter_3rd_cephalosporins(tbl, result = NULL, scope = "any", ...) + +filter_4th_cephalosporins(tbl, result = NULL, scope = "any", ...) + +filter_fluoroquinolones(tbl, result = NULL, scope = "any", ...) + +filter_glycopeptides(tbl, result = NULL, scope = "any", ...) + +filter_macrolides(tbl, result = NULL, scope = "any", ...) + +filter_tetracyclines(tbl, result = NULL, scope = "any", ...) +} +\arguments{ +\item{tbl}{a data set} + +\item{ab_class}{an antimicrobial class, like \code{"carbapenems"}} + +\item{result}{an antibiotic result: S, I or R (or a combination of more of them)} + +\item{scope}{the scope to check which variables to check, can be \code{"any"} (default) or \code{"all"}} + +\item{...}{parameters passed on to \code{\link[dplyr]{filter_at}}} +} +\description{ +Filter on specific antibiotic variables based on their class (ATC groups). +} +\details{ +The \code{\code{antibiotics}} data set will be searched for \code{ab_class} in the columns \code{atc_group1} and \code{atc_group2} (case-insensitive). Next, \code{tbl} will be checked for column names with a value in any abbreviations, codes or official names found in the \code{antibiotics} data set. +} +\examples{ +library(dplyr) + +# filter on isolates that have any result for any aminoglycoside +septic_patients \%>\% filter_aminoglycosides() + +# this is essentially the same as: +septic_patients \%>\% + filter_at(.vars = vars(c("gent", "tobr", "amik", "kana")), + .vars_predicate = any_vars(. \%in\% c("S", "I", "R"))) + + +# filter on isolates that show resistance to ANY aminoglycoside +septic_patients \%>\% filter_aminoglycosides("R") + +# filter on isolates that show resistance to ALL aminoglycosides +septic_patients \%>\% filter_aminoglycosides("R", "all") + +# filter on isolates that show resistance to +# any aminoglycoside and any fluoroquinolone +septic_patients \%>\% + filter_aminoglycosides("R", "any") \%>\% + filter_fluoroquinolones("R", "any") +} diff --git a/tests/testthat/test-filter_ab_class.R b/tests/testthat/test-filter_ab_class.R new file mode 100644 index 00000000..5bf8b842 --- /dev/null +++ b/tests/testthat/test-filter_ab_class.R @@ -0,0 +1,44 @@ +# ==================================================================== # +# TITLE # +# Antimicrobial Resistance (AMR) Analysis # +# # +# SOURCE # +# https://gitlab.com/msberends/AMR # +# # +# LICENCE # +# (c) 2019 Berends MS (m.s.berends@umcg.nl), Luz CF (c.f.luz@umcg.nl) # +# # +# This R package is free software; you can freely use and distribute # +# it for both personal and commercial purposes under the terms of the # +# GNU General Public License version 2.0 (GNU GPL-2), as published by # +# the Free Software Foundation. # +# # +# This R package was created for academic research and was publicly # +# released in the hope that it will be useful, but it comes WITHOUT # +# ANY WARRANTY OR LIABILITY. # +# Visit our website for more info: https://msberends.gitab.io/AMR. # +# ==================================================================== # + +context("filter_ab_class.R") + +test_that("ATC-group filtering works", { + library(dplyr) + expect_gt(septic_patients %>% filter_ab_class("carbapenem") %>% nrow(), 0) + expect_gt(septic_patients %>% filter_aminoglycosides() %>% nrow(), 0) + expect_gt(septic_patients %>% filter_carbapenems() %>% nrow(), 0) + expect_gt(septic_patients %>% filter_cephalosporins() %>% nrow(), 0) + expect_gt(septic_patients %>% filter_1st_cephalosporins() %>% nrow(), 0) + expect_gt(septic_patients %>% filter_2nd_cephalosporins() %>% nrow(), 0) + expect_gt(septic_patients %>% filter_3rd_cephalosporins() %>% nrow(), 0) + expect_gt(septic_patients %>% filter_4th_cephalosporins() %>% nrow(), 0) + expect_gt(septic_patients %>% filter_fluoroquinolones() %>% nrow(), 0) + expect_gt(septic_patients %>% filter_glycopeptides() %>% nrow(), 0) + expect_gt(septic_patients %>% filter_macrolides() %>% nrow(), 0) + expect_gt(septic_patients %>% filter_tetracyclines() %>% nrow(), 0) + + expect_gt(septic_patients %>% filter_carbapenems("R", "all") %>% nrow(), 0) + + expect_error(septic_patients %>% filter_carbapenems(result = "test")) + expect_error(septic_patients %>% filter_carbapenems(scope = "test")) + expect_warning(septic_patients %>% select(1:3) %>% filter_carbapenems()) +})