├── .Rbuildignore ├── .gitignore ├── .travis.yml ├── CRAN-RELEASE ├── DESCRIPTION ├── LICENSE.md ├── NAMESPACE ├── NEWS.md ├── R ├── assert.R ├── dap.R ├── ilap.R ├── lap.R ├── utils.R ├── vap.R ├── vapc.R └── vapr.R ├── README.Rmd ├── README.md ├── _pkgdown.yml ├── codecov.yml ├── cran-comments.md ├── dapr.Rproj ├── docs ├── CNAME ├── LICENSE.html ├── apple-touch-icon-120x120.png ├── apple-touch-icon-152x152.png ├── apple-touch-icon-180x180.png ├── apple-touch-icon-60x60.png ├── apple-touch-icon-76x76.png ├── apple-touch-icon.png ├── authors.html ├── docsearch.css ├── docsearch.js ├── extra.css ├── favicon-16x16.png ├── favicon-32x32.png ├── favicon.ico ├── index.html ├── link.svg ├── logo.png ├── news │ └── index.html ├── pkgdown.css ├── pkgdown.js ├── pkgdown.yml ├── reference │ ├── dap.html │ ├── figures │ │ └── logo.png │ ├── ilap.html │ ├── index.html │ ├── lap.html │ ├── vap.html │ ├── vapc.html │ └── vapr.html ├── sitemap.xml └── tools │ └── readme │ └── benchmark.png ├── man ├── dap.Rd ├── figures │ └── logo.png ├── ilap.Rd ├── lap.Rd ├── vap.Rd ├── vapc.Rd └── vapr.Rd ├── pkgdown ├── extra.css └── favicon │ ├── apple-touch-icon-120x120.png │ ├── apple-touch-icon-152x152.png │ ├── apple-touch-icon-180x180.png │ ├── apple-touch-icon-60x60.png │ ├── apple-touch-icon-76x76.png │ ├── apple-touch-icon.png │ ├── favicon-16x16.png │ ├── favicon-32x32.png │ └── favicon.ico ├── tests ├── testthat.R └── testthat │ ├── test-dap.R │ ├── test-lap.R │ ├── test-lap2.R │ ├── test-purrr-map.R │ └── test-vap.R └── tools └── readme └── benchmark.png /.Rbuildignore: -------------------------------------------------------------------------------- 1 | ^CRAN-RELEASE$ 2 | ^cran-comments\.md$ 3 | ^pkgdown$ 4 | ^_pkgdown\.yml$ 5 | ^docs$ 6 | ^LICENSE\.md$ 7 | ^codecov\.yml$ 8 | ^\.travis\.yml$ 9 | ^README\.Rmd$ 10 | ^.*\.Rproj$ 11 | ^\.Rproj\.user$ 12 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | .Rhistory 2 | .RData 3 | .Rproj.user 4 | .DS_Store 5 | 6 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | # R for travis: see documentation at https://docs.travis-ci.com/user/languages/r 2 | 3 | language: R 4 | sudo: false 5 | cache: packages 6 | after_success: 7 | - Rscript -e 'covr::codecov()' 8 | -------------------------------------------------------------------------------- /CRAN-RELEASE: -------------------------------------------------------------------------------- 1 | This package was submitted to CRAN on 2019-05-06. 2 | Once it is accepted, delete this file and tag the release (commit c2a9ab658f). 3 | -------------------------------------------------------------------------------- /DESCRIPTION: -------------------------------------------------------------------------------- 1 | Package: dapr 2 | Title: 'purrr'-Like Apply Functions Over Input Elements 3 | Version: 0.0.4 4 | Authors@R: 5 | person(given = "Michael W.", 6 | family = "Kearney", 7 | role = c("aut", "cre"), 8 | email = "kearneymw@missouri.edu", 9 | comment = c(ORCID = "0000-0002-0730-4694")) 10 | Description: An easy-to-use, dependency-free set of functions for iterating over 11 | elements of various input objects. Functions are wrappers around base 12 | apply()/lapply()/vapply() functions but designed to have similar 13 | functionality to the mapping functions in the 'purrr' package 14 | . Specifically, function names more explicitly 15 | communicate the expected class of the output and functions also allow for 16 | the convenient shortcut of '~ .x' instead of the more verbose 17 | 'function(.x) .x'. 18 | License: GPL-3 19 | Encoding: UTF-8 20 | Language: en 21 | LazyData: true 22 | RoxygenNote: 6.1.1 23 | URL: https://github.com/mkearney/dapr 24 | BugReports: https://github.com/mkearney/dapr/issues 25 | Suggests: 26 | testthat (>= 2.1.0), 27 | covr 28 | -------------------------------------------------------------------------------- /NAMESPACE: -------------------------------------------------------------------------------- 1 | # Generated by roxygen2: do not edit by hand 2 | 3 | S3method(dapc,default) 4 | S3method(dapc_if,default) 5 | S3method(dapr,default) 6 | S3method(dapr_if,default) 7 | S3method(ilap,default) 8 | S3method(lap,default) 9 | S3method(lap2,default) 10 | S3method(vap_chr,default) 11 | S3method(vap_dbl,default) 12 | S3method(vap_int,default) 13 | S3method(vap_lgl,default) 14 | export(dapc) 15 | export(dapc_if) 16 | export(dapr) 17 | export(dapr_if) 18 | export(ilap) 19 | export(lap) 20 | export(lap2) 21 | export(lapc) 22 | export(lapr) 23 | export(vap_chr) 24 | export(vap_dbl) 25 | export(vap_int) 26 | export(vap_lgl) 27 | export(vapc_chr) 28 | export(vapc_dbl) 29 | export(vapc_int) 30 | export(vapc_lgl) 31 | export(vapr_chr) 32 | export(vapr_dbl) 33 | export(vapr_int) 34 | export(vapr_lgl) 35 | -------------------------------------------------------------------------------- /NEWS.md: -------------------------------------------------------------------------------- 1 | # dapr 0.0.4 2 | 3 | * Functions can now return index names/positions 4 | * Added row and column-wise versions, i.e., `lapr()`, `vapc_chr()`, etc. 5 | * Improved documentation 6 | 7 | # dapr 0.0.3 8 | 9 | * Naming behaviors now mirror defaults of base `lapply()` and `vapply()`, so functions now return names 10 | * More consistent assert-based error messaging 11 | 12 | # dapr 0.0.2 13 | 14 | * Added tests and other documentation 15 | 16 | # dapr 0.0.1 17 | 18 | * Added a `NEWS.md` file to track changes to the package. 19 | * Initial commit with the `lap()`, `vap_*()`, and `dap*()` functions. 20 | -------------------------------------------------------------------------------- /R/assert.R: -------------------------------------------------------------------------------- 1 | 2 | assert_that <- function(..., env = parent.frame(), msg = NULL) { 3 | res <- see_if(..., env = env, msg = msg) 4 | if (res) return(TRUE) 5 | 6 | stop(assert_error(attr(res, "msg"))) 7 | } 8 | 9 | assert_error <- function (message, call = NULL) { 10 | class <- c("assert_error", "simpleError", "error", "condition") 11 | structure(list(message = message, call = call), class = class) 12 | } 13 | 14 | see_if <- function(..., env = parent.frame(), msg = NULL) { 15 | asserts <- eval(substitute(alist(...))) 16 | 17 | for (assertion in asserts) { 18 | res <- tryCatch({ 19 | eval(assertion, env) 20 | }, assert_error = function(e) { 21 | structure(FALSE, msg = e$message) 22 | }) 23 | 24 | if (!res) { 25 | if (is.null(msg)) 26 | msg <- get_message(res, assertion, env) 27 | return(structure(FALSE, msg = msg)) 28 | } 29 | } 30 | 31 | res 32 | } 33 | 34 | 35 | has_msg <- function(x) !is.null(attr(x, "msg", exact = TRUE)) 36 | 37 | get_message <- function(res, call, env = parent.frame()) { 38 | if (has_msg(res)) { 39 | return(attr(res, "msg")) 40 | } 41 | f <- eval(call[[1]], env) 42 | if (!is.primitive(f)) call <- match.call(f, call) 43 | fname <- deparse(call[[1]]) 44 | fail <- on_fail(f) %||% base_fs[[fname]] %||% fail_default 45 | fail(call, env) 46 | } 47 | 48 | fail_default <- function(call, env) { 49 | call_string <- deparse(call, width.cutoff = 60L) 50 | if (length(call_string) > 1L) { 51 | call_string <- paste0(call_string[1L], "...") 52 | } 53 | paste0(call_string, " is not TRUE") 54 | } 55 | 56 | on_fail <- function(x) attr(x, "fail") 57 | 58 | base_fs <- new.env(parent = emptyenv()) 59 | 60 | 61 | -------------------------------------------------------------------------------- /R/dap.R: -------------------------------------------------------------------------------- 1 | #' dap: Data frame apply functions 2 | #' 3 | #' Functions that apply expressions to input data objects and return data 4 | #' frames. 5 | #' 6 | #' @name dap 7 | #' @seealso \code{\link{lap}} \code{\link{vap}} 8 | NULL 9 | 10 | #' Data frame apply functions 11 | #' 12 | #' dapc: Apply function to columns of a data frame. 13 | #' 14 | #' @param .data Data frame input. 15 | #' @param .f Function to apply to element (columns or rows). This can be written 16 | #' as a single function name e.g., \code{mean}, a formula-like function call 17 | #' where '.x' is assumed to be the iterated over element of input data e.g., 18 | #' \code{~ mean(.x)}, or an in-line function definition e.g., 19 | #' \code{function(x) mean(x)}. 20 | #' @param ... Other values passed to function call. 21 | #' @return A data frame 22 | #' @family dap 23 | #' @export 24 | #' @rdname dap 25 | dapc <- function(.data, .f, ...) UseMethod("dapc") 26 | 27 | #' @export 28 | dapc.default <- function(.data, .f, ...) { 29 | assert_that(is_vector(.data)) 30 | 31 | if (is_lang(.f)) { 32 | e <- call_env() 33 | .f <- eval(.f, envir = e)[[2]] 34 | .data[] <- lapply(.data, function(.x) { 35 | eval(.f, list(.x = .x), e) 36 | }) 37 | } else { 38 | .data[] <- lapply(.data, .f, ...) 39 | } 40 | .data 41 | } 42 | 43 | #' @rdname dap 44 | #' @description dapr: Apply function to rows of a data frame. 45 | #' @family dap 46 | #' @export 47 | dapr <- function(.data, .f, ...) UseMethod("dapr") 48 | 49 | #' @export 50 | dapr.default <- function(.data, .f, ...) { 51 | assert_that(is_vector(.data)) 52 | 53 | if (is_lang(.f)) { 54 | e <- call_env() 55 | .f <- eval(.f, envir = e)[[2]] 56 | .data[seq_len(nrow(.data)), ] <- t(apply(.data, 1, 57 | function(.x) eval(.f, list(.x = .x), e) 58 | )) 59 | } else { 60 | .data[seq_len(nrow(.data)), ] <- t(apply(.data, 1, .f, ...)) 61 | } 62 | .data 63 | } 64 | 65 | 66 | 67 | #' @rdname dap 68 | #' @description dapc_if: Apply function to certain columns of a data frame. 69 | #' @inheritParams dap 70 | #' @param .predicate Logical vector or expression evaluating to a logical vector. 71 | #' If not a logical vector, this can be written as a single function name 72 | #' e.g., \code{is.numeric}, a formula-like function call where '.x' is assumed 73 | #' to be the iterated over element of input data e.g., 74 | #' \code{~ is.numeric(.x)}, or an in-line function definition e.g., 75 | #' \code{function(x) is.numeric(x)}. Regardless, if a logical vector is not 76 | #' provided, this expression must return a logical vector of the same length 77 | #' as the input .data object. 78 | #' 79 | #' The resulting logical vector is used to determine which elements (rows or 80 | #' columns) to iterate over with the .f function/expression. 81 | #' @family dap 82 | #' @export 83 | dapc_if <- function(.data, .predicate, .f, ...) UseMethod("dapc_if") 84 | 85 | #' @export 86 | dapc_if.default <- function(.data, .predicate, .f, ...) { 87 | assert_that(is_vector(.data)) 88 | 89 | if (is.logical(.predicate)) { 90 | lg <- .predicate 91 | } else if (is_lang(.predicate)) { 92 | e <- call_env() 93 | .predicate <- eval(.predicate, envir = e)[[2]] 94 | lg <- vapply(.data, 95 | function(.x) eval(.predicate, list(.x = .x), e), 96 | FUN.VALUE = logical(1)) 97 | } else { 98 | lg <- vapply(.data, .predicate, 99 | FUN.VALUE = logical(1)) 100 | } 101 | assert_that(is.logical(lg)) 102 | 103 | if (is_lang(.f)) { 104 | e <- call_env() 105 | .f <- eval(.f, envir = e)[[2]] 106 | .data[lg] <- lapply(.data[lg], 107 | function(.x) eval(.f, list(.x = .x), e) 108 | ) 109 | } else { 110 | .data[lg] <- lapply(.data[lg], .f, ...) 111 | } 112 | .data 113 | } 114 | 115 | 116 | 117 | #' @rdname dap 118 | #' @description dapr_if: Apply function to certain rows of a data frame. 119 | #' @inheritParams dap 120 | #' @family dap 121 | #' @export 122 | dapr_if <- function(.data, .predicate, .f, ...) UseMethod("dapr_if") 123 | 124 | #' @export 125 | dapr_if.default <- function(.data, .predicate, .f, ...) { 126 | assert_that(is_vector(.data)) 127 | 128 | if (is.logical(.predicate)) { 129 | lg <- .predicate 130 | } else if (is_lang(.predicate)) { 131 | e <- call_env() 132 | .predicate <- eval(.predicate, envir = e)[[2]] 133 | lg <- unlist(apply(.data, 1, 134 | function(.x) eval(.predicate, list(.x = .x), e) 135 | )) 136 | } else { 137 | lg <- vapply(.data, .predicate, 138 | FUN.VALUE = logical(1)) 139 | } 140 | assert_that(is.logical(lg)) 141 | if (sum(lg) == 0) return(.data) 142 | 143 | if (is_lang(.f)) { 144 | e <- call_env() 145 | .f <- eval(.f, envir = e)[[2]] 146 | .data[lg, ] <- t(apply(.data[lg, ], 1, 147 | function(.x) eval(.f, list(.x = .x), e) 148 | )) 149 | } else { 150 | .data[lg, ] <- t(apply(.data[lg, ], 1, .f, ...)) 151 | } 152 | .data 153 | } 154 | -------------------------------------------------------------------------------- /R/ilap.R: -------------------------------------------------------------------------------- 1 | 2 | #' Iterator list apply 3 | #' 4 | #' ilap: Iterate over sequence length of input and return list(s) 5 | #' 6 | #' @param .data Object representing the sequence length, used as ".i" in the .f 7 | #' expression. If matrix or data frame, sequence length will be determined by 8 | #' the number of columns. If integer, then it will be passed directly onto 9 | #' function call, otherwise the object will be converted into a sequence from 10 | #' 1 to the length of the object. 11 | #' @param .f Function to apply to each element (as an integer position) of input 12 | #' object. This can be written as a single function name e.g., \code{mean}, a 13 | #' formula-like function call where '.i' is assumed to be the integer position 14 | #' of input data object e.g., \code{~ mean(mtcars[[.i]])}, or an in-line 15 | #' function definition e.g., \code{function(x) mean(mtcars[[x]])}. 16 | #' @param ... Other values passed to function call. 17 | #' @return A list 18 | #' @family lap 19 | #' @examples 20 | #' 21 | #' ## return string list 22 | #' ilap(1:10, ~ paste0(letters[.i], rev(LETTERS)[.i])) 23 | #' 24 | #' ## return list of columns 25 | #' ilap(mtcars, ~ c(row.names(mtcars)[.i], mtcars$wt[.i])) 26 | #' 27 | #' @export 28 | ilap <- function(.data, .f, ...) UseMethod("ilap") 29 | 30 | #' @export 31 | ilap.default <- function(.data, .f, ...) { 32 | if (!is.integer(.data)) { 33 | .data <- seq_along(.data) 34 | } 35 | if (is_lang(.f)) { 36 | e <- call_env() 37 | lapply(.data, function(.i) { 38 | eval(eval(.f, envir = e)[[2]], list(.i = .i), e) 39 | }) 40 | } else { 41 | lapply(.data, .f, ...) 42 | } 43 | } 44 | -------------------------------------------------------------------------------- /R/lap.R: -------------------------------------------------------------------------------- 1 | #' lap: List apply functions 2 | #' 3 | #' Function(s) that apply expressions to input data objects and return lists. 4 | #' 5 | #' @name lap 6 | #' @seealso \code{\link{dap}} \code{\link{vap}} 7 | NULL 8 | 9 | #' List apply 10 | #' 11 | #' lap: Iterate over input and return list(s) 12 | #' 13 | #' @param .data Input object–numeric, character, list, data frame, etc.–over 14 | #' which elements will be iterated. If matrix or data frame, each 15 | #' column will be treated as the elements which are to be iterated over. 16 | #' @param .f Function to apply to each element of input object. This can be 17 | #' written as a single function name e.g., \code{mean}, a formula-like 18 | #' function call where '.x' is assumed to be the iterated over element of 19 | #' input data e.g., \code{~ mean(.x)}, or an in-line function definition e.g., 20 | #' \code{function(x) mean(x)}. 21 | #' @param ... Other values passed to function call. 22 | #' @return A list 23 | #' @family lap 24 | #' @examples 25 | #' 26 | #' ## return string list 27 | #' lap(letters, ~ paste0(.x, ".")) 28 | #' 29 | #' ## return list of columns 30 | #' lap(mtcars[1:5, ], as.character) 31 | #' 32 | #' ## map over two vectors 33 | #' lap2(letters, LETTERS, ~ paste0(.x, .y, .x, .y)) 34 | #' 35 | #' @export 36 | lap <- function(.data, .f, ...) UseMethod("lap") 37 | 38 | #' @export 39 | lap.default <- function(.data, .f, ...) { 40 | assert_that(is_vector(.data)) 41 | 42 | if (is_lang(.f)) { 43 | e <- call_env() 44 | .f <- eval(.f, envir = e)[[2]] 45 | lapply(.data, function(.x) { 46 | eval(.f, list(.x = .x), e) 47 | }) 48 | } else { 49 | lapply(.data, .f, ...) 50 | } 51 | } 52 | 53 | 54 | #' List apply-to-row 55 | #' 56 | #' lapr: Iterate over input rows and return list(s) 57 | #' 58 | #' @rdname lap 59 | #' @inheritParams lap 60 | #' @export 61 | lapr <- function(.data, .f, ...) { 62 | assert_that(is_2d(.data)) 63 | if (is_lang(.f)) { 64 | e <- call_env() 65 | .f <- eval(.f, envir = e)[[2]] 66 | lapply(seq_len(nrow(.data)), function(.i) { 67 | eval(.f, list(.x = .data[.i, , drop = FALSE]), e) 68 | }) 69 | } else { 70 | lapply(seq_len(nrow(.data)), function(.i) { 71 | .f(.data[.i, , drop = FALSE], ...) 72 | }) 73 | } 74 | } 75 | 76 | #' List apply-to-column 77 | #' 78 | #' lapr: Iterate over input columbs and return list(s) 79 | #' 80 | #' @rdname lap 81 | #' @inheritParams lap 82 | #' @export 83 | lapc <- function(.data, .f, ...) { 84 | assert_that(is_2d(.data)) 85 | if (is_lang(.f)) { 86 | e <- call_env() 87 | .f <- eval(.f, envir = e)[[2]] 88 | lapply(seq_len(ncol(.data)), function(.i) { 89 | eval(.f, list(.x = .data[, .i, drop = FALSE]), e) 90 | }) 91 | } else { 92 | lapply(seq_len(ncol(.data)), function(.i) { 93 | .f(.data[, .i, drop = FALSE], ...) 94 | }) 95 | } 96 | } 97 | 98 | 99 | #' @rdname lap 100 | #' @inheritParams lap 101 | #' @param .x First data vector input (for lap2) 102 | #' @param .y Second data vector input (for lap2) 103 | #' @export 104 | lap2 <- function(.x, .y, .f, ...) UseMethod("lap2") 105 | 106 | #' @export 107 | lap2.default <- function(.x, .y, .f, ...) { 108 | assert_that(is_vector(.x)) 109 | assert_that(is_vector(.y)) 110 | assert_that(length(.x) == length(.y)) 111 | 112 | if (is_lang(.f)) { 113 | e <- call_env() 114 | .f <- eval(.f, envir = e)[[2]] 115 | # .f <- as.call(.f) 116 | # tfse::cat_line(class(.f)) 117 | # tfse::cat_line(deparse(.f)) 118 | # mapply( 119 | # .f, .x, .y, SIMPLIFY = FALSE 120 | # ) 121 | lapply(seq_along(.x), function(.i) { 122 | eval(.f, list(.x = .x[[.i]], .y = .y[[.i]]), e) 123 | }) 124 | } else { 125 | mapply(.f, .x, .y, ..., SIMPLIFY = FALSE) 126 | } 127 | } 128 | -------------------------------------------------------------------------------- /R/utils.R: -------------------------------------------------------------------------------- 1 | is_lang <- function(x) identical(typeof(x), "language") 2 | 3 | call_env <- function(n = 1) parent.frame(n + 1) 4 | 5 | is_vector <- function(x) { 6 | if (is.atomic(x) || is.list(x) || is.call(x)) { 7 | return(TRUE) 8 | } 9 | FALSE 10 | } 11 | 12 | "%||%" <- function(a, b) if (is.null(a)) b else a 13 | 14 | is_2d <- function(x) length(dim(x)) == 2 15 | 16 | -------------------------------------------------------------------------------- /R/vap.R: -------------------------------------------------------------------------------- 1 | #' vap: Vector apply functions 2 | #' 3 | #' Functions that apply expressions to input objects and return atomic vectors 4 | #' e.g., numeric (double), integer, character, logical. 5 | #' 6 | #' @name vap 7 | #' @family vap 8 | #' @seealso \code{\link{lap}} \code{\link{dap}} 9 | NULL 10 | 11 | #' Vector apply double 12 | #' 13 | #' vap_dbl: Iterate over input and return double(s) 14 | #' 15 | #' @param .data Input object–numeric, character, list, data frame, etc.–over 16 | #' which elements will be iterated. If matrix or data frame, each 17 | #' column will be treated as an element. 18 | #' @param .f Action to apply to each element of \code{.data}. The action can be 19 | #' articulated in one of the four following ways: 20 | #' \enumerate{ 21 | #' \item supplying a function object (e.g., \code{mean}) 22 | #' \item defining a function (in-line; e.g., \code{function(x) mean(x)}) 23 | #' \item specifying a formula-like call where '.x' is assumed to be the iterated 24 | #' over element of \code{.data} (e.g., \code{~ mean(.x)}) 25 | #' \item providing a name or position of \code{.data} to return (e.g., 26 | #' \code{1}, \code{"varname"}, etc.) 27 | #' } 28 | #' @return A double vector 29 | #' @export 30 | #' @examples 31 | #' 32 | #' ## character 33 | #' vap_chr(letters, ~ paste0(.x, ".")) 34 | #' 35 | #' ## double 36 | #' vap_dbl(rnorm(4), round, 3) 37 | #' 38 | #' ## logical 39 | #' vap_lgl(letters, ~ .x %in% c("a", "e", "i", "o", "u")) 40 | #' 41 | #' ## integer 42 | #' vap_int(as.data.frame(replicate(10, sample(1:10))), 8) 43 | #' 44 | #' @rdname vap 45 | vap_dbl <- function(.data, .f, ...) UseMethod("vap_dbl") 46 | 47 | #' @export 48 | vap_dbl.default <- function(.data, .f, ...) { 49 | if (is_lang(.f)) { 50 | e <- call_env() 51 | .f <- eval(.f, envir = e)[[2]] 52 | vapply(.data, 53 | function(.x) eval(.f, list(.x = .x), e), 54 | FUN.VALUE = numeric(1)) 55 | } else if (is.atomic(.f)) { 56 | as.numeric(getElement(.data, .f)) 57 | } else { 58 | vapply(.data, .f, ..., 59 | FUN.VALUE = numeric(1)) 60 | } 61 | } 62 | 63 | 64 | #' Vector apply character 65 | #' 66 | #' vap_chr: Iterate over input and return character(s) 67 | #' 68 | #' @inheritParams vap_dbl 69 | #' @return A character vector 70 | #' @param ... Other values passed to function call. 71 | #' @export 72 | #' @rdname vap 73 | vap_chr <- function(.data, .f, ...) UseMethod("vap_chr") 74 | 75 | #' @export 76 | vap_chr.default <- function(.data, .f, ...) { 77 | if (is_lang(.f)) { 78 | e <- call_env() 79 | .f <- eval(.f, envir = e)[[2]] 80 | vapply(.data, 81 | function(.x) eval(.f, list(.x = .x), e), 82 | FUN.VALUE = character(1)) 83 | } else if (is.atomic(.f)) { 84 | as.character(getElement(.data, .f)) 85 | } else { 86 | vapply(.data, .f, ..., 87 | FUN.VALUE = character(1)) 88 | } 89 | } 90 | 91 | 92 | #' Vector apply logical 93 | #' 94 | #' vap_lgl: Iterate over input and return logical(s) 95 | #' 96 | #' @inheritParams vap_dbl 97 | #' @return A logical vector 98 | #' @export 99 | #' @rdname vap 100 | vap_lgl <- function(.data, .f, ...) UseMethod("vap_lgl") 101 | 102 | #' @export 103 | vap_lgl.default <- function(.data, .f, ...) { 104 | if (is_lang(.f)) { 105 | e <- call_env() 106 | .f <- eval(.f, envir = e)[[2]] 107 | vapply(.data, 108 | function(.x) eval(.f, list(.x = .x), e), 109 | FUN.VALUE = logical(1)) 110 | } else if (is.atomic(.f)) { 111 | as.logical(getElement(.data, .f)) 112 | } else { 113 | vapply(.data, .f, ..., 114 | FUN.VALUE = logical(1)) 115 | } 116 | } 117 | 118 | 119 | 120 | #' Vector apply integer 121 | #' 122 | #' vap_int: Iterate over input and return integer(s) 123 | #' 124 | #' @inheritParams vap_dbl 125 | #' @return An integer vector 126 | #' @export 127 | #' @rdname vap 128 | vap_int <- function(.data, .f, ...) UseMethod("vap_int") 129 | 130 | #' @export 131 | vap_int.default <- function(.data, .f, ...) { 132 | if (is_lang(.f)) { 133 | e <- call_env() 134 | .f <- eval(.f, envir = e)[[2]] 135 | vapply(.data, 136 | function(.x) eval(.f, list(.x = .x), e), 137 | FUN.VALUE = integer(1)) 138 | } else if (is.atomic(.f)) { 139 | as.integer(getElement(.data, .f)) 140 | } else { 141 | vapply(.data, .f, ..., 142 | FUN.VALUE = integer(1)) 143 | } 144 | } 145 | 146 | 147 | 148 | 149 | 150 | 151 | 152 | -------------------------------------------------------------------------------- /R/vapc.R: -------------------------------------------------------------------------------- 1 | #' vapr: Vector apply-to-column functions 2 | #' 3 | #' Functions that apply expressions to the columns of input objects and return 4 | #' atomic vectors e.g., numeric (double), integer, character, logical. 5 | #' 6 | #' @name vapc 7 | #' @family vap 8 | #' @seealso \code{\link{lap}} \code{\link{dap}} 9 | NULL 10 | 11 | #' Vector apply-to-column character 12 | #' 13 | #' vapc_chr: Iterate over input \strong{columns} and return \strong{character(s)} 14 | #' 15 | #' @param .data Input object–must be two-dimensional (e.g., matrix, data.frame) 16 | #' –over which the second dimension (columns) will be iterated 17 | #' @inheritParams vap_dbl 18 | #' @return A character vector 19 | #' @export 20 | #' @rdname vapc 21 | vapc_chr <- function(.data, .f, ...) { 22 | assert_that(is_2d(.data)) 23 | if (is_lang(.f)) { 24 | e <- call_env() 25 | .f <- eval(.f, envir = e)[[2]] 26 | vapply(seq_len(ncol(.data)), function(.i) { 27 | eval(.f, list(.x = .data[, .i, drop = FALSE]), e) 28 | }, FUN.VALUE = character(1)) 29 | } else if (is.atomic(.f)) { 30 | vapply(seq_len(ncol(.data)), function(.i) { 31 | as.character(.data[.f, .i, drop = TRUE]) 32 | }, FUN.VALUE = character(1)) 33 | } else { 34 | vapply(seq_len(ncol(.data)), function(.i) { 35 | .f(.data[, .i, drop = FALSE], ...) 36 | }, FUN.VALUE = character(1)) 37 | } 38 | } 39 | 40 | 41 | #' Vector apply-to-column numeric 42 | #' 43 | #' vapc_dbl: Iterate over input \strong{columns} and return \strong{numeric(s)} 44 | #' 45 | #' @inheritParams vapc_chr 46 | #' @return A numeric vector 47 | #' @export 48 | #' @rdname vapc 49 | vapc_dbl <- function(.data, .f, ...) { 50 | assert_that(is_2d(.data)) 51 | if (is_lang(.f)) { 52 | e <- call_env() 53 | .f <- eval(.f, envir = e)[[2]] 54 | vapply(seq_len(ncol(.data)), function(.i) { 55 | eval(.f, list(.x = .data[, .i, drop = FALSE]), e) 56 | }, FUN.VALUE = numeric(1)) 57 | } else if (is.atomic(.f)) { 58 | vapply(seq_len(ncol(.data)), function(.i) { 59 | as.numeric(.data[.f, .i, drop = TRUE]) 60 | }, FUN.VALUE = numeric(1)) 61 | } else { 62 | vapply(seq_len(ncol(.data)), function(.i) { 63 | .f(.data[, .i, drop = FALSE], ...) 64 | }, FUN.VALUE = numeric(1)) 65 | } 66 | } 67 | 68 | #' Vector apply-to-column logical 69 | #' 70 | #' vapc_lgl: Iterate over input \strong{columns} and return \strong{logical(s)} 71 | #' 72 | #' @inheritParams vapc_chr 73 | #' @return A logical vector 74 | #' @export 75 | #' @rdname vapc 76 | vapc_lgl <- function(.data, .f, ...) { 77 | assert_that(is_2d(.data)) 78 | if (is_lang(.f)) { 79 | e <- call_env() 80 | .f <- eval(.f, envir = e)[[2]] 81 | vapply(seq_len(ncol(.data)), function(.i) { 82 | eval(.f, list(.x = .data[, .i, drop = FALSE]), e) 83 | }, FUN.VALUE = logical(1)) 84 | } else if (is.atomic(.f)) { 85 | vapply(seq_len(ncol(.data)), function(.i) { 86 | as.logical(.data[.f, .i, drop = TRUE]) 87 | }, FUN.VALUE = logical(1)) 88 | } else { 89 | vapply(seq_len(ncol(.data)), function(.i) { 90 | .f(.data[, .i, drop = FALSE], ...) 91 | }, FUN.VALUE = logical(1)) 92 | } 93 | } 94 | 95 | #' Vector apply-to-column integer 96 | #' 97 | #' vapc_int: Iterate over input \strong{columns} and return \strong{integer(s)} 98 | #' 99 | #' @inheritParams vapc_chr 100 | #' @return An integer vector 101 | #' @export 102 | #' @rdname vapc 103 | vapc_int <- function(.data, .f, ...) { 104 | assert_that(is_2d(.data)) 105 | if (is_lang(.f)) { 106 | e <- call_env() 107 | .f <- eval(.f, envir = e)[[2]] 108 | vapply(seq_len(ncol(.data)), function(.i) { 109 | eval(.f, list(.x = .data[, .i, drop = FALSE]), e) 110 | }, FUN.VALUE = integer(1)) 111 | } else if (is.atomic(.f)) { 112 | vapply(seq_len(ncol(.data)), function(.i) { 113 | as.integer(.data[.f, .i, drop = TRUE]) 114 | }, FUN.VALUE = integer(1)) 115 | } else { 116 | vapply(seq_len(ncol(.data)), function(.i) { 117 | .f(.data[, .i, drop = FALSE], ...) 118 | }, FUN.VALUE = integer(1)) 119 | } 120 | } 121 | -------------------------------------------------------------------------------- /R/vapr.R: -------------------------------------------------------------------------------- 1 | #' vapr: Vector apply-to-row functions 2 | #' 3 | #' Functions that apply expressions to the rows of input objects and return 4 | #' atomic vectors e.g., numeric (double), integer, character, logical. 5 | #' 6 | #' @name vapr 7 | #' @family vap 8 | #' @seealso \code{\link{lap}} \code{\link{dap}} 9 | NULL 10 | 11 | #' Vector apply-to-row character 12 | #' 13 | #' vapr_chr: Iterate over input \strong{rows} and return \strong{character(s)} 14 | #' 15 | #' @param .data Input object–must be two-dimensional (e.g., matrix, data.frame) 16 | #' –over which the first dimension (rows) will be iterated 17 | #' @inheritParams vap_dbl 18 | #' @return A character vector 19 | #' @export 20 | #' @rdname vapr 21 | vapr_chr <- function(.data, .f, ...) { 22 | assert_that(is_2d(.data)) 23 | if (is_lang(.f)) { 24 | e <- call_env() 25 | .f <- eval(.f, envir = e)[[2]] 26 | vapply(seq_len(nrow(.data)), function(.i) { 27 | eval(.f, list(.x = .data[.i, , drop = FALSE]), e) 28 | }, FUN.VALUE = character(1)) 29 | } else if (is.atomic(.f)) { 30 | vapply(seq_len(nrow(.data)), function(.i) { 31 | as.character(.data[.i, .f, drop = TRUE]) 32 | }, FUN.VALUE = character(1)) 33 | } else { 34 | vapply(seq_len(nrow(.data)), function(.i) { 35 | .f(.data[.i, , drop = FALSE], ...) 36 | }, FUN.VALUE = character(1)) 37 | } 38 | } 39 | 40 | 41 | #' Vector apply-to-row numeric 42 | #' 43 | #' vapr_dbl: Iterate over input \strong{rows} and return \strong{numeric(s)} 44 | #' 45 | #' @inheritParams vapr_chr 46 | #' @return A numeric vector 47 | #' @export 48 | #' @rdname vapr 49 | vapr_dbl <- function(.data, .f, ...) { 50 | assert_that(is_2d(.data)) 51 | if (is_lang(.f)) { 52 | e <- call_env() 53 | .f <- eval(.f, envir = e)[[2]] 54 | vapply(seq_len(nrow(.data)), function(.i) { 55 | eval(.f, list(.x = .data[.i, , drop = FALSE]), e) 56 | }, FUN.VALUE = numeric(1)) 57 | } else if (is.atomic(.f)) { 58 | vapply(seq_len(nrow(.data)), function(.i) { 59 | as.numeric(.data[.i, .f, drop = TRUE]) 60 | }, FUN.VALUE = numeric(1)) 61 | } else { 62 | vapply(seq_len(nrow(.data)), function(.i) { 63 | .f(.data[.i, , drop = FALSE], ...) 64 | }, FUN.VALUE = numeric(1)) 65 | } 66 | } 67 | 68 | #' Vector apply-to-row logical 69 | #' 70 | #' vapr_lgl: Iterate over input \strong{rows} and return \strong{logical(s)} 71 | #' 72 | #' @inheritParams vapr_chr 73 | #' @return A logical vector 74 | #' @export 75 | #' @rdname vapr 76 | vapr_lgl <- function(.data, .f, ...) { 77 | assert_that(is_2d(.data)) 78 | if (is_lang(.f)) { 79 | e <- call_env() 80 | .f <- eval(.f, envir = e)[[2]] 81 | vapply(seq_len(nrow(.data)), function(.i) { 82 | eval(.f, list(.x = .data[.i, , drop = FALSE]), e) 83 | }, FUN.VALUE = logical(1)) 84 | } else if (is.atomic(.f)) { 85 | vapply(seq_len(nrow(.data)), function(.i) { 86 | as.logical(.data[.i, .f, drop = TRUE]) 87 | }, FUN.VALUE = logical(1)) 88 | } else { 89 | vapply(seq_len(nrow(.data)), function(.i) { 90 | .f(.data[.i, , drop = FALSE], ...) 91 | }, FUN.VALUE = logical(1)) 92 | } 93 | } 94 | 95 | #' Vector apply-to-row integer 96 | #' 97 | #' vapr_int: Iterate over input \strong{rows} and return \strong{integer(s)} 98 | #' 99 | #' @inheritParams vapr_chr 100 | #' @return An integer vector 101 | #' @export 102 | #' @rdname vapr 103 | vapr_int <- function(.data, .f, ...) { 104 | assert_that(is_2d(.data)) 105 | if (is_lang(.f)) { 106 | e <- call_env() 107 | .f <- eval(.f, envir = e)[[2]] 108 | vapply(seq_len(nrow(.data)), function(.i) { 109 | eval(.f, list(.x = .data[.i, , drop = FALSE]), e) 110 | }, FUN.VALUE = integer(1)) 111 | } else if (is.atomic(.f)) { 112 | vapply(seq_len(nrow(.data)), function(.i) { 113 | as.integer(.data[.i, .f, drop = TRUE]) 114 | }, FUN.VALUE = integer(1)) 115 | } else { 116 | vapply(seq_len(nrow(.data)), function(.i) { 117 | .f(.data[.i, , drop = FALSE], ...) 118 | }, FUN.VALUE = integer(1)) 119 | } 120 | } 121 | -------------------------------------------------------------------------------- /README.Rmd: -------------------------------------------------------------------------------- 1 | --- 2 | output: github_document 3 | --- 4 | 5 | 6 | 7 | ```{r setup, include = FALSE} 8 | knitr::opts_chunk$set(echo = TRUE, collapse = TRUE, comment = "#>") 9 | library(dapr) 10 | ``` 11 | # dapr 12 | 13 | [![Build status](https://travis-ci.org/mkearney/dapr.svg?branch=master)](https://travis-ci.org/mkearney/dapr) 14 | [![CRAN status](https://www.r-pkg.org/badges/version/dapr)](https://cran.r-project.org/package=dapr) 15 | [![Coverage Status](https://codecov.io/gh/mkearney/dapr/branch/master/graph/badge.svg)](https://codecov.io/gh/mkearney/dapr?branch=master) 16 | [![DOI](https://zenodo.org/badge/DOI/10.5281/zenodo.2528504.svg)](https://doi.org/10.5281/zenodo.2528504) 17 | ![Downloads](https://cranlogs.r-pkg.org/badges/dapr?color=yellowgreen) 18 | ![Downloads](https://cranlogs.r-pkg.org/badges/grand-total/dapr?color=dd69b4) 19 | [![lifecycle](https://img.shields.io/badge/lifecycle-experimental-orange.svg)](https://www.tidyverse.org/lifecycle/#experimental) 20 | 21 | Dependency-free purrr-like apply/map/iterate functions 22 | 23 | ## Installation 24 | 25 | Install the development version from Github with: 26 | 27 | ``` r 28 | ## install remotes pkg if not already 29 | if (!requireNamespace("remotes", quietly = TRUE)) { 30 | install.packages("remotes") 31 | } 32 | 33 | ## install from github 34 | remotes::install_github("mkearney/dapr") 35 | ``` 36 | 37 | ## {dapr} vs. {base} & {purrr}? 38 | **{dapr}** provides the ease and consistency of [**{purrr}**](https://purrr.tidyverse.org), 39 | (see also: simple benchmark results plot below) including use of `~` and `.x`, 40 | without all the dependencies. In other words, use **{dapr}** when you want a 41 | purrr-like experience but you need a lightweight solution. 42 | 43 |

44 | 45 |

46 | 47 | ## Use 48 | 49 | Function names use the convention `*ap()` where **`*`** is the first letter of output data type. 50 | 51 | + vap for **vectors** 52 | + lap for **lists** 53 | + dap for **data frames** 54 | 55 | Common inputs: 56 | 57 | + `.data` Input object–numeric, character, list, data frame, etc.–over which elements will be iterated. If matrix or data frame, each column will be treated as the elements which are to be iterated over. 58 | + `.f` Function to apply to each element of input object. This can be written as a single function name e.g., `mean`, a formula-like function call where `.x` is assumed to be the iterated over element of input data e.g., `~ mean(.x)`, or an in-line function definition e.g., `function(x) mean(x)`. 59 | 60 | ### Vectors 61 | 62 | Functions that apply expressions to input data objects and return atomic vectors 63 | e.g., numeric (double), character, logical. 64 | 65 | + **`vap_dbl()`** Iterate and return **numeric** vector. 66 | + **`vap_int()`** Iterate and return **integer** vector. 67 | + **`vap_lgl()`** Iterate and return **logical** vector. 68 | + **`vap_chr()`** Iterate and return **character** vector. 69 | 70 | ```{r} 71 | ## create data 72 | set.seed(2018) 73 | d <- replicate(5, rnorm(10), simplify = FALSE) 74 | e <- replicate(5, sample(letters, 10), simplify = FALSE) 75 | 76 | ## numeric 77 | vap_dbl(d, ~ mean(.x)) 78 | 79 | ## integer 80 | vap_int(d, length) 81 | 82 | ## logical 83 | vap_lgl(d, ~ max(.x) > 3) 84 | 85 | ## character 86 | vap_chr(e, paste, collapse = "") 87 | ``` 88 | 89 | ### Lists 90 | 91 | Function(s) that apply expressions to input data objects and return lists. 92 | 93 | + **`lap()`** Iterate and return a **list** vector. 94 | 95 | ```{r} 96 | ## list of strings 97 | lap(e[1:2], ~ paste0(.x, ".")) 98 | ``` 99 | 100 | + **`ilap()`** Iterate over sequence length `.i` (instead of `.x`) and return a **list** vector. 101 | 102 | ```{r} 103 | ## list of strings 104 | ilap(1:4, ~ paste0(letters[.i], rev(LETTERS)[.i])) 105 | ``` 106 | 107 | ### Data frames 108 | 109 | Functions that apply expressions to input data objects and return data frames. 110 | 111 | + **`dap*()`** Iterate and return a **data frame** 112 | - **`dapc()`** Iterate over **columns** 113 | - **`dapr()`** Iterate over **rows** 114 | + **`dap*_if()`** Conditionally iterate 115 | - **`dapc_if()`** Conditionally iterate over **columns** 116 | - **`dapr_if()`** Conditionally iterate over **rows** 117 | 118 | ```{r} 119 | ## some data 120 | d <- data.frame( 121 | a = letters[1:3], 122 | b = rnorm(3), 123 | c = rnorm(3), 124 | stringsAsFactors = FALSE 125 | ) 126 | 127 | ## column explicit (same as dap) 128 | dapc(d[-1], ~ round(.x, 2)) 129 | 130 | ## rows 131 | dapr(d[-1], round, 3) 132 | 133 | ## conditional COLUMNS 134 | dapc_if(d, is.numeric, ~ round(.x, 4)) 135 | 136 | ## conditional ROWS 137 | dapr_if(d[-1], ~ sum(.x) >= -.7, ~ round(.x, 0)) 138 | ``` 139 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | # dapr 5 | 6 | [![Build 7 | status](https://travis-ci.org/mkearney/dapr.svg?branch=master)](https://travis-ci.org/mkearney/dapr) 8 | [![CRAN 9 | status](https://www.r-pkg.org/badges/version/dapr)](https://cran.r-project.org/package=dapr) 10 | [![Coverage 11 | Status](https://codecov.io/gh/mkearney/dapr/branch/master/graph/badge.svg)](https://codecov.io/gh/mkearney/dapr?branch=master) 12 | [![DOI](https://zenodo.org/badge/DOI/10.5281/zenodo.2528504.svg)](https://doi.org/10.5281/zenodo.2528504) 13 | ![Downloads](https://cranlogs.r-pkg.org/badges/dapr?color=yellowgreen) 14 | ![Downloads](https://cranlogs.r-pkg.org/badges/grand-total/dapr?color=dd69b4) 15 | [![lifecycle](https://img.shields.io/badge/lifecycle-experimental-orange.svg)](https://www.tidyverse.org/lifecycle/#experimental) 16 | 17 | Dependency-free purrr-like apply/map/iterate functions 18 | 19 | ## Installation 20 | 21 | Install the development version from Github with: 22 | 23 | ``` r 24 | ## install remotes pkg if not already 25 | if (!requireNamespace("remotes", quietly = TRUE)) { 26 | install.packages("remotes") 27 | } 28 | 29 | ## install from github 30 | remotes::install_github("mkearney/dapr") 31 | ``` 32 | 33 | ## {dapr} vs. {base} & {purrr}? 34 | 35 | **{dapr}** provides the ease and consistency of 36 | [**{purrr}**](https://purrr.tidyverse.org), (see also: simple benchmark 37 | results plot below) including use of `~` and `.x`, without all the 38 | dependencies. In other words, use **{dapr}** when you want a purrr-like 39 | experience but you need a lightweight solution. 40 | 41 |

42 | 43 | 44 | 45 |

46 | 47 | ## Use 48 | 49 | Function names use the convention `*ap()` where **`*`** is the first 50 | letter of output data type. 51 | 52 | - vap 53 | for **vectors** 54 | - lap 55 | for **lists** 56 | - dap 57 | for **data frames** 58 | 59 | Common inputs: 60 | 61 | - `.data` Input object–numeric, character, list, data frame, etc.–over 62 | which elements will be iterated. If matrix or data frame, each 63 | column will be treated as the elements which are to be iterated 64 | over. 65 | - `.f` Function to apply to each element of input object. This can be 66 | written as a single function name e.g., `mean`, a formula-like 67 | function call where `.x` is assumed to be the iterated over element 68 | of input data e.g., `~ mean(.x)`, or an in-line function definition 69 | e.g., `function(x) mean(x)`. 70 | 71 | ### Vectors 72 | 73 | Functions that apply expressions to input data objects and return atomic 74 | vectors e.g., numeric (double), character, logical. 75 | 76 | - **`vap_dbl()`** Iterate and return **numeric** vector. 77 | - **`vap_int()`** Iterate and return **integer** vector. 78 | - **`vap_lgl()`** Iterate and return **logical** vector. 79 | - **`vap_chr()`** Iterate and return **character** vector. 80 | 81 | 82 | 83 | ``` r 84 | ## create data 85 | set.seed(2018) 86 | d <- replicate(5, rnorm(10), simplify = FALSE) 87 | e <- replicate(5, sample(letters, 10), simplify = FALSE) 88 | 89 | ## numeric 90 | vap_dbl(d, ~ mean(.x)) 91 | #> [1] 0.26934527 -0.55232322 0.05559290 -0.06253258 -0.11183760 92 | 93 | ## integer 94 | vap_int(d, length) 95 | #> [1] 10 10 10 10 10 96 | 97 | ## logical 98 | vap_lgl(d, ~ max(.x) > 3) 99 | #> [1] FALSE FALSE FALSE FALSE FALSE 100 | 101 | ## character 102 | vap_chr(e, paste, collapse = "") 103 | #> [1] "hizjpgcexk" "rbeovimtxh" "ujrimwgvzs" "euwrlytgbj" "qkrhylgmnx" 104 | ``` 105 | 106 | ### Lists 107 | 108 | Function(s) that apply expressions to input data objects and return 109 | lists. 110 | 111 | - **`lap()`** Iterate and return a **list** vector. 112 | 113 | 114 | 115 | ``` r 116 | ## list of strings 117 | lap(e[1:2], ~ paste0(.x, ".")) 118 | #> [[1]] 119 | #> [1] "h." "i." "z." "j." "p." "g." "c." "e." "x." "k." 120 | #> 121 | #> [[2]] 122 | #> [1] "r." "b." "e." "o." "v." "i." "m." "t." "x." "h." 123 | ``` 124 | 125 | - **`ilap()`** Iterate over sequence length `.i` (instead of `.x`) and 126 | return a **list** vector. 127 | 128 | 129 | 130 | ``` r 131 | ## list of strings 132 | ilap(1:4, ~ paste0(letters[.i], rev(LETTERS)[.i])) 133 | #> [[1]] 134 | #> [1] "aZ" 135 | #> 136 | #> [[2]] 137 | #> [1] "bY" 138 | #> 139 | #> [[3]] 140 | #> [1] "cX" 141 | #> 142 | #> [[4]] 143 | #> [1] "dW" 144 | ``` 145 | 146 | ### Data frames 147 | 148 | Functions that apply expressions to input data objects and return data 149 | frames. 150 | 151 | - **`dap*()`** Iterate and return a **data frame** 152 | - **`dapc()`** Iterate over **columns** 153 | - **`dapr()`** Iterate over **rows** 154 | - **`dap*_if()`** Conditionally iterate 155 | - **`dapc_if()`** Conditionally iterate over **columns** 156 | - **`dapr_if()`** Conditionally iterate over **rows** 157 | 158 | 159 | 160 | ``` r 161 | ## some data 162 | d <- data.frame( 163 | a = letters[1:3], 164 | b = rnorm(3), 165 | c = rnorm(3), 166 | stringsAsFactors = FALSE 167 | ) 168 | 169 | ## column explicit (same as dap) 170 | dapc(d[-1], ~ round(.x, 2)) 171 | #> b c 172 | #> 1 -0.50 -0.09 173 | #> 2 -1.87 1.08 174 | #> 3 0.74 -1.36 175 | 176 | ## rows 177 | dapr(d[-1], round, 3) 178 | #> b c 179 | #> 1 -0.499 -0.089 180 | #> 2 -1.869 1.081 181 | #> 3 0.743 -1.365 182 | 183 | ## conditional COLUMNS 184 | dapc_if(d, is.numeric, ~ round(.x, 4)) 185 | #> a b c 186 | #> 1 a -0.4994 -0.0892 187 | #> 2 b -1.8686 1.0812 188 | #> 3 c 0.7434 -1.3646 189 | 190 | ## conditional ROWS 191 | dapr_if(d[-1], ~ sum(.x) >= -.7, ~ round(.x, 0)) 192 | #> b c 193 | #> 1 0.000000 0.000000 194 | #> 2 -1.868615 1.081164 195 | #> 3 1.000000 -1.000000 196 | ``` 197 | -------------------------------------------------------------------------------- /_pkgdown.yml: -------------------------------------------------------------------------------- 1 | destination: docs 2 | 3 | url: https://dapr.mikewk.com 4 | 5 | template: 6 | ganalytics: "UA-124886828-1" 7 | 8 | authors: 9 | Michael W. Kearney: 10 | href: https://mikewk.com 11 | navbar: 12 | right: 13 | - icon: fa-github fa-lg 14 | href: https://github.com/mkearney/dapr 15 | -------------------------------------------------------------------------------- /codecov.yml: -------------------------------------------------------------------------------- 1 | comment: false 2 | 3 | coverage: 4 | status: 5 | project: 6 | default: 7 | target: auto 8 | threshold: 1% 9 | patch: 10 | default: 11 | target: auto 12 | threshold: 1% 13 | -------------------------------------------------------------------------------- /cran-comments.md: -------------------------------------------------------------------------------- 1 | ## Test environments 2 | * local OS X install, R 3.5.3 3 | * ubuntu 14.04 (on travis-ci), R 3.5.3 4 | * win-builder (devel and release) 5 | 6 | ## R CMD check results 7 | 8 | 0 errors | 0 warnings | 0 notes 9 | -------------------------------------------------------------------------------- /dapr.Rproj: -------------------------------------------------------------------------------- 1 | Version: 1.0 2 | 3 | RestoreWorkspace: No 4 | SaveWorkspace: No 5 | AlwaysSaveHistory: Default 6 | 7 | EnableCodeIndexing: Yes 8 | UseSpacesForTab: Yes 9 | NumSpacesForTab: 2 10 | Encoding: UTF-8 11 | 12 | RnwWeave: Sweave 13 | LaTeX: pdfLaTeX 14 | 15 | AutoAppendNewline: Yes 16 | StripTrailingWhitespace: Yes 17 | 18 | BuildType: Package 19 | PackageUseDevtools: Yes 20 | PackageInstallArgs: --no-multiarch --with-keep.source 21 | PackageRoxygenize: rd,collate,namespace 22 | -------------------------------------------------------------------------------- /docs/CNAME: -------------------------------------------------------------------------------- 1 | dapr.mikewk.com 2 | -------------------------------------------------------------------------------- /docs/apple-touch-icon-120x120.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/docs/apple-touch-icon-120x120.png -------------------------------------------------------------------------------- /docs/apple-touch-icon-152x152.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/docs/apple-touch-icon-152x152.png -------------------------------------------------------------------------------- /docs/apple-touch-icon-180x180.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/docs/apple-touch-icon-180x180.png -------------------------------------------------------------------------------- /docs/apple-touch-icon-60x60.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/docs/apple-touch-icon-60x60.png -------------------------------------------------------------------------------- /docs/apple-touch-icon-76x76.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/docs/apple-touch-icon-76x76.png -------------------------------------------------------------------------------- /docs/apple-touch-icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/docs/apple-touch-icon.png -------------------------------------------------------------------------------- /docs/authors.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | Authors • dapr 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 57 | 58 | 59 | 60 | 61 | 62 |
63 |
64 | 107 | 108 | 109 |
110 | 111 |
112 |
113 | 116 | 117 | 123 | 124 |
125 | 126 |
127 | 128 | 129 | 138 |
139 | 140 | 141 | 142 | 143 | 144 | 145 | -------------------------------------------------------------------------------- /docs/docsearch.css: -------------------------------------------------------------------------------- 1 | /* Docsearch -------------------------------------------------------------- */ 2 | /* 3 | Source: https://github.com/algolia/docsearch/ 4 | License: MIT 5 | */ 6 | 7 | .algolia-autocomplete { 8 | display: block; 9 | -webkit-box-flex: 1; 10 | -ms-flex: 1; 11 | flex: 1 12 | } 13 | 14 | .algolia-autocomplete .ds-dropdown-menu { 15 | width: 100%; 16 | min-width: none; 17 | max-width: none; 18 | padding: .75rem 0; 19 | background-color: #fff; 20 | background-clip: padding-box; 21 | border: 1px solid rgba(0, 0, 0, .1); 22 | box-shadow: 0 .5rem 1rem rgba(0, 0, 0, .175); 23 | } 24 | 25 | @media (min-width:768px) { 26 | .algolia-autocomplete .ds-dropdown-menu { 27 | width: 175% 28 | } 29 | } 30 | 31 | .algolia-autocomplete .ds-dropdown-menu::before { 32 | display: none 33 | } 34 | 35 | .algolia-autocomplete .ds-dropdown-menu [class^=ds-dataset-] { 36 | padding: 0; 37 | background-color: rgb(255,255,255); 38 | border: 0; 39 | max-height: 80vh; 40 | } 41 | 42 | .algolia-autocomplete .ds-dropdown-menu .ds-suggestions { 43 | margin-top: 0 44 | } 45 | 46 | .algolia-autocomplete .algolia-docsearch-suggestion { 47 | padding: 0; 48 | overflow: visible 49 | } 50 | 51 | .algolia-autocomplete .algolia-docsearch-suggestion--category-header { 52 | padding: .125rem 1rem; 53 | margin-top: 0; 54 | font-size: 1.3em; 55 | font-weight: 500; 56 | color: #00008B; 57 | border-bottom: 0 58 | } 59 | 60 | .algolia-autocomplete .algolia-docsearch-suggestion--wrapper { 61 | float: none; 62 | padding-top: 0 63 | } 64 | 65 | .algolia-autocomplete .algolia-docsearch-suggestion--subcategory-column { 66 | float: none; 67 | width: auto; 68 | padding: 0; 69 | text-align: left 70 | } 71 | 72 | .algolia-autocomplete .algolia-docsearch-suggestion--content { 73 | float: none; 74 | width: auto; 75 | padding: 0 76 | } 77 | 78 | .algolia-autocomplete .algolia-docsearch-suggestion--content::before { 79 | display: none 80 | } 81 | 82 | .algolia-autocomplete .ds-suggestion:not(:first-child) .algolia-docsearch-suggestion--category-header { 83 | padding-top: .75rem; 84 | margin-top: .75rem; 85 | border-top: 1px solid rgba(0, 0, 0, .1) 86 | } 87 | 88 | .algolia-autocomplete .ds-suggestion .algolia-docsearch-suggestion--subcategory-column { 89 | display: block; 90 | padding: .1rem 1rem; 91 | margin-bottom: 0.1; 92 | font-size: 1.0em; 93 | font-weight: 400 94 | /* display: none */ 95 | } 96 | 97 | .algolia-autocomplete .algolia-docsearch-suggestion--title { 98 | display: block; 99 | padding: .25rem 1rem; 100 | margin-bottom: 0; 101 | font-size: 0.9em; 102 | font-weight: 400 103 | } 104 | 105 | .algolia-autocomplete .algolia-docsearch-suggestion--text { 106 | padding: 0 1rem .5rem; 107 | margin-top: -.25rem; 108 | font-size: 0.8em; 109 | font-weight: 400; 110 | line-height: 1.25 111 | } 112 | 113 | .algolia-autocomplete .algolia-docsearch-footer { 114 | width: 110px; 115 | height: 20px; 116 | z-index: 3; 117 | margin-top: 10.66667px; 118 | float: right; 119 | font-size: 0; 120 | line-height: 0; 121 | } 122 | 123 | .algolia-autocomplete .algolia-docsearch-footer--logo { 124 | background-image: url("data:image/svg+xml;utf8,"); 125 | background-repeat: no-repeat; 126 | background-position: 50%; 127 | background-size: 100%; 128 | overflow: hidden; 129 | text-indent: -9000px; 130 | width: 100%; 131 | height: 100%; 132 | display: block; 133 | transform: translate(-8px); 134 | } 135 | 136 | .algolia-autocomplete .algolia-docsearch-suggestion--highlight { 137 | color: #FF8C00; 138 | background: rgba(232, 189, 54, 0.1) 139 | } 140 | 141 | 142 | .algolia-autocomplete .algolia-docsearch-suggestion--text .algolia-docsearch-suggestion--highlight { 143 | box-shadow: inset 0 -2px 0 0 rgba(105, 105, 105, .5) 144 | } 145 | 146 | .algolia-autocomplete .ds-suggestion.ds-cursor .algolia-docsearch-suggestion--content { 147 | background-color: rgba(192, 192, 192, .15) 148 | } 149 | -------------------------------------------------------------------------------- /docs/docsearch.js: -------------------------------------------------------------------------------- 1 | $(function() { 2 | 3 | // register a handler to move the focus to the search bar 4 | // upon pressing shift + "/" (i.e. "?") 5 | $(document).on('keydown', function(e) { 6 | if (e.shiftKey && e.keyCode == 191) { 7 | e.preventDefault(); 8 | $("#search-input").focus(); 9 | } 10 | }); 11 | 12 | $(document).ready(function() { 13 | // do keyword highlighting 14 | /* modified from https://jsfiddle.net/julmot/bL6bb5oo/ */ 15 | var mark = function() { 16 | 17 | var referrer = document.URL ; 18 | var paramKey = "q" ; 19 | 20 | if (referrer.indexOf("?") !== -1) { 21 | var qs = referrer.substr(referrer.indexOf('?') + 1); 22 | var qs_noanchor = qs.split('#')[0]; 23 | var qsa = qs_noanchor.split('&'); 24 | var keyword = ""; 25 | 26 | for (var i = 0; i < qsa.length; i++) { 27 | var currentParam = qsa[i].split('='); 28 | 29 | if (currentParam.length !== 2) { 30 | continue; 31 | } 32 | 33 | if (currentParam[0] == paramKey) { 34 | keyword = decodeURIComponent(currentParam[1].replace(/\+/g, "%20")); 35 | } 36 | } 37 | 38 | if (keyword !== "") { 39 | $(".contents").unmark({ 40 | done: function() { 41 | $(".contents").mark(keyword); 42 | } 43 | }); 44 | } 45 | } 46 | }; 47 | 48 | mark(); 49 | }); 50 | }); 51 | 52 | /* Search term highlighting ------------------------------*/ 53 | 54 | function matchedWords(hit) { 55 | var words = []; 56 | 57 | var hierarchy = hit._highlightResult.hierarchy; 58 | // loop to fetch from lvl0, lvl1, etc. 59 | for (var idx in hierarchy) { 60 | words = words.concat(hierarchy[idx].matchedWords); 61 | } 62 | 63 | var content = hit._highlightResult.content; 64 | if (content) { 65 | words = words.concat(content.matchedWords); 66 | } 67 | 68 | // return unique words 69 | var words_uniq = [...new Set(words)]; 70 | return words_uniq; 71 | } 72 | 73 | function updateHitURL(hit) { 74 | 75 | var words = matchedWords(hit); 76 | var url = ""; 77 | 78 | if (hit.anchor) { 79 | url = hit.url_without_anchor + '?q=' + escape(words.join(" ")) + '#' + hit.anchor; 80 | } else { 81 | url = hit.url + '?q=' + escape(words.join(" ")); 82 | } 83 | 84 | return url; 85 | } 86 | -------------------------------------------------------------------------------- /docs/extra.css: -------------------------------------------------------------------------------- 1 | 2 | @import url("https://fonts.googleapis.com/css?family=Roboto:400,400i,700,700i,900"); 3 | 4 | @import url(https://cdn.rawgit.com/tonsky/FiraCode/1.205/distr/fira_code.css); 5 | 6 | body { 7 | font-family: Roboto, sans-serif; 8 | font-size: 16px; 9 | line-height: 1.5; 10 | font-weight: 400; 11 | margin: .5em auto 5em auto; 12 | } 13 | 14 | h1, h2, h3, h4, .h1, .h2, .h3, .h4 { 15 | font-family: Roboto, sans-serif; 16 | font-weight: 900; 17 | } 18 | 19 | h1 {font-size: 2.1em} 20 | h2 {font-size: 1.8em} 21 | h3 {font-size: 1.6em} 22 | h4 {font-size: 1.3em} 23 | 24 | code { 25 | font-family: "Fira Code", Consolas, Monaco, Menlo, Inconsolata, monospace; 26 | } 27 | 28 | pre { 29 | box-shadow: 30 | rgba(0, 0, 0, 0.1) 0 2px 3px 1px, 31 | rgba(0, 0, 0, 0.1) 0 1px 3px 1px, 32 | rgba(0, 0, 0, 0.2) 0 1px 1px -1px; 33 | font-size: .80em; 34 | margin-left: auto; 35 | width: 98%; 36 | margin-right: auto; 37 | line-height: 1.4em; 38 | font-family: "Fira Code", Consolas, Monaco, Menlo, Inconsolata, monospace; 39 | } 40 | 41 | div.sourceCode { 42 | overflow: visible; 43 | } 44 | 45 | pre.sourceCode { 46 | margin-left: auto; 47 | margin-right: auto; 48 | } 49 | 50 | p { 51 | margin: 1.5em 0; 52 | } 53 | 54 | strong { 55 | font-family: Roboto, sans-serif; 56 | font-weight: 900; 57 | } 58 | 59 | strong code { 60 | font-family: "Fira Code", Consolas, Monaco, Menlo, Inconsolata, monospace; 61 | font-weight: 700; 62 | } 63 | 64 | code span.co, .co { 65 | color: #828f96; 66 | } 67 | 68 | code span.ot, .ot { 69 | color: #ddaa00; 70 | } 71 | 72 | .navbar-default { 73 | box-shadow: 74 | rgba(0, 0, 0, 0.1) 0 2px 3px 1px, 75 | rgba(0, 0, 0, 0.1) 0 1px 3px 1px, 76 | rgba(0, 0, 0, 0.2) 0 1px 1px -1px; 77 | background-color: #f3f3f3; 78 | border-color: #eee; 79 | } 80 | -------------------------------------------------------------------------------- /docs/favicon-16x16.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/docs/favicon-16x16.png -------------------------------------------------------------------------------- /docs/favicon-32x32.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/docs/favicon-32x32.png -------------------------------------------------------------------------------- /docs/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/docs/favicon.ico -------------------------------------------------------------------------------- /docs/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 'purrr'-Like Apply Functions Over Input Elements • dapr 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 28 | 29 | 30 | 34 | 35 | 36 |
37 |
80 | 81 | 82 | 83 |
84 |
85 | 86 | 87 | 88 | 89 | 90 |
91 | 94 |

Build status CRAN status Coverage Status DOI DownloadsDownloadslifecycle

95 |

Dependency-free purrr-like apply/map/iterate functions

96 |
97 |

98 | Installation

99 |

Install the development version from Github with:

100 |
## install remotes pkg if not already
101 | if (!requireNamespace("remotes", quietly = TRUE)) {
102 |   install.packages("remotes")
103 | }
104 | 
105 | ## install from github
106 | remotes::install_github("mkearney/dapr")
107 |
108 |
109 |

110 | {dapr} vs. {base} & {purrr}?

111 |

{dapr} provides the ease and consistency of {purrr}, (see also: simple benchmark results plot below) including use of ~ and .x, without all the dependencies. In other words, use {dapr} when you want a purrr-like experience but you need a lightweight solution.

112 |

113 |

114 |
115 |
116 |

117 | Use

118 |

Function names use the convention *ap() where * is the first letter of output data type.

119 |
    120 |
  • 121 | vap for vectors 122 |
  • 123 |
  • 124 | lap for lists 125 |
  • 126 |
  • 127 | dap for data frames 128 |
  • 129 |
130 |

Common inputs:

131 |
    132 |
  • 133 | .data Input object–numeric, character, list, data frame, etc.–over which elements will be iterated. If matrix or data frame, each column will be treated as the elements which are to be iterated over.
  • 134 |
  • 135 | .f Function to apply to each element of input object. This can be written as a single function name e.g., mean, a formula-like function call where .x is assumed to be the iterated over element of input data e.g., ~ mean(.x), or an in-line function definition e.g., function(x) mean(x).
  • 136 |
137 |
138 |

139 | Vectors

140 |

Functions that apply expressions to input data objects and return atomic vectors e.g., numeric (double), character, logical.

141 |
    142 |
  • 143 | vap_dbl() Iterate and return numeric vector.
  • 144 |
  • 145 | vap_int() Iterate and return integer vector.
  • 146 |
  • 147 | vap_lgl() Iterate and return logical vector.
  • 148 |
  • 149 | vap_chr() Iterate and return character vector.
  • 150 |
151 |
## create data
152 | set.seed(2018)
153 | d <- replicate(5, rnorm(10), simplify = FALSE)
154 | e <- replicate(5, sample(letters, 10), simplify = FALSE)
155 | 
156 | ## numeric
157 | vap_dbl(d, ~ mean(.x))
158 | #> [1]  0.26934527 -0.55232322  0.05559290 -0.06253258 -0.11183760
159 | 
160 | ## integer
161 | vap_int(d, length)
162 | #> [1] 10 10 10 10 10
163 | 
164 | ## logical
165 | vap_lgl(d, ~ max(.x) > 3)
166 | #> [1] FALSE FALSE FALSE FALSE FALSE
167 | 
168 | ## character
169 | vap_chr(e, paste, collapse = "")
170 | #> [1] "hizjpgcexk" "rbeovimtxh" "ujrimwgvzs" "euwrlytgbj" "qkrhylgmnx"
171 |
172 |
173 |

174 | Lists

175 |

Function(s) that apply expressions to input data objects and return lists.

176 |
    177 |
  • 178 | lap() Iterate and return a list vector.
  • 179 |
180 |
## list of strings
181 | lap(e[1:2], ~ paste0(.x, "."))
182 | #> [[1]]
183 | #>  [1] "h." "i." "z." "j." "p." "g." "c." "e." "x." "k."
184 | #> 
185 | #> [[2]]
186 | #>  [1] "r." "b." "e." "o." "v." "i." "m." "t." "x." "h."
187 |
    188 |
  • 189 | ilap() Iterate over sequence length .i (instead of .x) and return a list vector.
  • 190 |
191 |
## list of strings
192 | ilap(1:4, ~ paste0(letters[.i], rev(LETTERS)[.i]))
193 | #> [[1]]
194 | #> [1] "aZ"
195 | #> 
196 | #> [[2]]
197 | #> [1] "bY"
198 | #> 
199 | #> [[3]]
200 | #> [1] "cX"
201 | #> 
202 | #> [[4]]
203 | #> [1] "dW"
204 |
205 |
206 |

207 | Data frames

208 |

Functions that apply expressions to input data objects and return data frames.

209 |
    210 |
  • 211 | dap*() Iterate and return a data frame 212 |
      213 |
    • 214 | dapc() Iterate over columns 215 |
    • 216 |
    • 217 | dapr() Iterate over rows 218 |
    • 219 |
    220 |
  • 221 |
  • 222 | dap*_if() Conditionally iterate 223 |
      224 |
    • 225 | dapc_if() Conditionally iterate over columns 226 |
    • 227 |
    • 228 | dapr_if() Conditionally iterate over rows 229 |
    • 230 |
    231 |
  • 232 |
233 |
## some data
234 | d <- data.frame(
235 |   a = letters[1:3],
236 |   b = rnorm(3),
237 |   c = rnorm(3),
238 |   stringsAsFactors = FALSE
239 | )
240 | 
241 | ## column explicit (same as dap)
242 | dapc(d[-1], ~ round(.x, 2))
243 | #>       b     c
244 | #> 1 -0.50 -0.09
245 | #> 2 -1.87  1.08
246 | #> 3  0.74 -1.36
247 | 
248 | ## rows
249 | dapr(d[-1], round, 3)
250 | #>        b      c
251 | #> 1 -0.499 -0.089
252 | #> 2 -1.869  1.081
253 | #> 3  0.743 -1.365
254 | 
255 | ## conditional COLUMNS
256 | dapc_if(d, is.numeric, ~ round(.x, 4))
257 | #>   a       b       c
258 | #> 1 a -0.4994 -0.0892
259 | #> 2 b -1.8686  1.0812
260 | #> 3 c  0.7434 -1.3646
261 | 
262 | ## conditional ROWS
263 | dapr_if(d[-1], ~ sum(.x) >= -.7, ~ round(.x, 0))
264 | #>           b         c
265 | #> 1  0.000000  0.000000
266 | #> 2 -1.868615  1.081164
267 | #> 3  1.000000 -1.000000
268 |
269 |
270 |
271 |
272 | 273 | 301 | 302 |
303 | 304 | 305 | 313 |
314 | 315 | 316 | 317 | 318 | 319 | -------------------------------------------------------------------------------- /docs/link.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 5 | 8 | 12 | 13 | -------------------------------------------------------------------------------- /docs/logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/docs/logo.png -------------------------------------------------------------------------------- /docs/news/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | Changelog • dapr 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 57 | 58 | 59 | 60 | 61 | 62 |
63 |
64 | 107 | 108 | 109 |
110 | 111 |
112 |
113 | 117 | 118 |
119 |

120 | dapr 0.0.4 Unreleased 121 |

122 |
    123 |
  • Functions can now return index names/positions
  • 124 |
  • Added row and column-wise versions, i.e., lapr(), vapc_chr(), etc.
  • 125 |
  • Improved documentation
  • 126 |
127 |
128 |
129 |

130 | dapr 0.0.3 2019-05-06 131 |

132 |
    133 |
  • Naming behaviors now mirror defaults of base lapply() and vapply(), so functions now return names
  • 134 |
  • More consistent assert-based error messaging
  • 135 |
136 |
137 |
138 |

139 | dapr 0.0.2 2019-01-20 140 |

141 |
    142 |
  • Added tests and other documentation
  • 143 |
144 |
145 |
146 |

147 | dapr 0.0.1 Unreleased 148 |

149 |
    150 |
  • Added a NEWS.md file to track changes to the package.
  • 151 |
  • Initial commit with the lap(), vap_*(), and dap*() functions.
  • 152 |
153 |
154 |
155 | 156 | 167 | 168 |
169 | 170 | 179 |
180 | 181 | 182 | 183 | 184 | 185 | 186 | -------------------------------------------------------------------------------- /docs/pkgdown.css: -------------------------------------------------------------------------------- 1 | /* Sticky footer */ 2 | 3 | /** 4 | * Basic idea: https://philipwalton.github.io/solved-by-flexbox/demos/sticky-footer/ 5 | * Details: https://github.com/philipwalton/solved-by-flexbox/blob/master/assets/css/components/site.css 6 | * 7 | * .Site -> body > .container 8 | * .Site-content -> body > .container .row 9 | * .footer -> footer 10 | * 11 | * Key idea seems to be to ensure that .container and __all its parents__ 12 | * have height set to 100% 13 | * 14 | */ 15 | 16 | html, body { 17 | height: 100%; 18 | } 19 | 20 | body > .container { 21 | display: flex; 22 | height: 100%; 23 | flex-direction: column; 24 | 25 | padding-top: 60px; 26 | } 27 | 28 | body > .container .row { 29 | flex: 1 0 auto; 30 | } 31 | 32 | footer { 33 | margin-top: 45px; 34 | padding: 35px 0 36px; 35 | border-top: 1px solid #e5e5e5; 36 | color: #666; 37 | display: flex; 38 | flex-shrink: 0; 39 | } 40 | footer p { 41 | margin-bottom: 0; 42 | } 43 | footer div { 44 | flex: 1; 45 | } 46 | footer .pkgdown { 47 | text-align: right; 48 | } 49 | footer p { 50 | margin-bottom: 0; 51 | } 52 | 53 | img.icon { 54 | float: right; 55 | } 56 | 57 | img { 58 | max-width: 100%; 59 | } 60 | 61 | /* Fix bug in bootstrap (only seen in firefox) */ 62 | summary { 63 | display: list-item; 64 | } 65 | 66 | /* Typographic tweaking ---------------------------------*/ 67 | 68 | .contents .page-header { 69 | margin-top: calc(-60px + 1em); 70 | } 71 | 72 | /* Section anchors ---------------------------------*/ 73 | 74 | a.anchor { 75 | margin-left: -30px; 76 | display:inline-block; 77 | width: 30px; 78 | height: 30px; 79 | visibility: hidden; 80 | 81 | background-image: url(./link.svg); 82 | background-repeat: no-repeat; 83 | background-size: 20px 20px; 84 | background-position: center center; 85 | } 86 | 87 | .hasAnchor:hover a.anchor { 88 | visibility: visible; 89 | } 90 | 91 | @media (max-width: 767px) { 92 | .hasAnchor:hover a.anchor { 93 | visibility: hidden; 94 | } 95 | } 96 | 97 | 98 | /* Fixes for fixed navbar --------------------------*/ 99 | 100 | .contents h1, .contents h2, .contents h3, .contents h4 { 101 | padding-top: 60px; 102 | margin-top: -40px; 103 | } 104 | 105 | /* Static header placement on mobile devices */ 106 | @media (max-width: 767px) { 107 | .navbar-fixed-top { 108 | position: absolute; 109 | } 110 | .navbar { 111 | padding: 0; 112 | } 113 | } 114 | 115 | 116 | /* Sidebar --------------------------*/ 117 | 118 | #sidebar { 119 | margin-top: 30px; 120 | } 121 | #sidebar h2 { 122 | font-size: 1.5em; 123 | margin-top: 1em; 124 | } 125 | 126 | #sidebar h2:first-child { 127 | margin-top: 0; 128 | } 129 | 130 | #sidebar .list-unstyled li { 131 | margin-bottom: 0.5em; 132 | } 133 | 134 | .orcid { 135 | height: 16px; 136 | vertical-align: middle; 137 | } 138 | 139 | /* Reference index & topics ----------------------------------------------- */ 140 | 141 | .ref-index th {font-weight: normal;} 142 | 143 | .ref-index td {vertical-align: top;} 144 | .ref-index .icon {width: 40px;} 145 | .ref-index .alias {width: 40%;} 146 | .ref-index-icons .alias {width: calc(40% - 40px);} 147 | .ref-index .title {width: 60%;} 148 | 149 | .ref-arguments th {text-align: right; padding-right: 10px;} 150 | .ref-arguments th, .ref-arguments td {vertical-align: top;} 151 | .ref-arguments .name {width: 20%;} 152 | .ref-arguments .desc {width: 80%;} 153 | 154 | /* Nice scrolling for wide elements --------------------------------------- */ 155 | 156 | table { 157 | display: block; 158 | overflow: auto; 159 | } 160 | 161 | /* Syntax highlighting ---------------------------------------------------- */ 162 | 163 | pre { 164 | word-wrap: normal; 165 | word-break: normal; 166 | border: 1px solid #eee; 167 | } 168 | 169 | pre, code { 170 | background-color: #f8f8f8; 171 | color: #333; 172 | } 173 | 174 | pre code { 175 | overflow: auto; 176 | word-wrap: normal; 177 | white-space: pre; 178 | } 179 | 180 | pre .img { 181 | margin: 5px 0; 182 | } 183 | 184 | pre .img img { 185 | background-color: #fff; 186 | display: block; 187 | height: auto; 188 | } 189 | 190 | code a, pre a { 191 | color: #375f84; 192 | } 193 | 194 | a.sourceLine:hover { 195 | text-decoration: none; 196 | } 197 | 198 | .fl {color: #1514b5;} 199 | .fu {color: #000000;} /* function */ 200 | .ch,.st {color: #036a07;} /* string */ 201 | .kw {color: #264D66;} /* keyword */ 202 | .co {color: #888888;} /* comment */ 203 | 204 | .message { color: black; font-weight: bolder;} 205 | .error { color: orange; font-weight: bolder;} 206 | .warning { color: #6A0366; font-weight: bolder;} 207 | 208 | /* Clipboard --------------------------*/ 209 | 210 | .hasCopyButton { 211 | position: relative; 212 | } 213 | 214 | .btn-copy-ex { 215 | position: absolute; 216 | right: 0; 217 | top: 0; 218 | visibility: hidden; 219 | } 220 | 221 | .hasCopyButton:hover button.btn-copy-ex { 222 | visibility: visible; 223 | } 224 | 225 | /* mark.js ----------------------------*/ 226 | 227 | mark { 228 | background-color: rgba(255, 255, 51, 0.5); 229 | border-bottom: 2px solid rgba(255, 153, 51, 0.3); 230 | padding: 1px; 231 | } 232 | 233 | /* vertical spacing after htmlwidgets */ 234 | .html-widget { 235 | margin-bottom: 10px; 236 | } 237 | -------------------------------------------------------------------------------- /docs/pkgdown.js: -------------------------------------------------------------------------------- 1 | /* http://gregfranko.com/blog/jquery-best-practices/ */ 2 | (function($) { 3 | $(function() { 4 | 5 | $("#sidebar") 6 | .stick_in_parent({offset_top: 40}) 7 | .on('sticky_kit:bottom', function(e) { 8 | $(this).parent().css('position', 'static'); 9 | }) 10 | .on('sticky_kit:unbottom', function(e) { 11 | $(this).parent().css('position', 'relative'); 12 | }); 13 | 14 | $('body').scrollspy({ 15 | target: '#sidebar', 16 | offset: 60 17 | }); 18 | 19 | $('[data-toggle="tooltip"]').tooltip(); 20 | 21 | var cur_path = paths(location.pathname); 22 | var links = $("#navbar ul li a"); 23 | var max_length = -1; 24 | var pos = -1; 25 | for (var i = 0; i < links.length; i++) { 26 | if (links[i].getAttribute("href") === "#") 27 | continue; 28 | // Ignore external links 29 | if (links[i].host !== location.host) 30 | continue; 31 | 32 | var nav_path = paths(links[i].pathname); 33 | 34 | var length = prefix_length(nav_path, cur_path); 35 | if (length > max_length) { 36 | max_length = length; 37 | pos = i; 38 | } 39 | } 40 | 41 | // Add class to parent
  • , and enclosing
  • if in dropdown 42 | if (pos >= 0) { 43 | var menu_anchor = $(links[pos]); 44 | menu_anchor.parent().addClass("active"); 45 | menu_anchor.closest("li.dropdown").addClass("active"); 46 | } 47 | }); 48 | 49 | function paths(pathname) { 50 | var pieces = pathname.split("/"); 51 | pieces.shift(); // always starts with / 52 | 53 | var end = pieces[pieces.length - 1]; 54 | if (end === "index.html" || end === "") 55 | pieces.pop(); 56 | return(pieces); 57 | } 58 | 59 | // Returns -1 if not found 60 | function prefix_length(needle, haystack) { 61 | if (needle.length > haystack.length) 62 | return(-1); 63 | 64 | // Special case for length-0 haystack, since for loop won't run 65 | if (haystack.length === 0) { 66 | return(needle.length === 0 ? 0 : -1); 67 | } 68 | 69 | for (var i = 0; i < haystack.length; i++) { 70 | if (needle[i] != haystack[i]) 71 | return(i); 72 | } 73 | 74 | return(haystack.length); 75 | } 76 | 77 | /* Clipboard --------------------------*/ 78 | 79 | function changeTooltipMessage(element, msg) { 80 | var tooltipOriginalTitle=element.getAttribute('data-original-title'); 81 | element.setAttribute('data-original-title', msg); 82 | $(element).tooltip('show'); 83 | element.setAttribute('data-original-title', tooltipOriginalTitle); 84 | } 85 | 86 | if(ClipboardJS.isSupported()) { 87 | $(document).ready(function() { 88 | var copyButton = ""; 89 | 90 | $(".examples, div.sourceCode").addClass("hasCopyButton"); 91 | 92 | // Insert copy buttons: 93 | $(copyButton).prependTo(".hasCopyButton"); 94 | 95 | // Initialize tooltips: 96 | $('.btn-copy-ex').tooltip({container: 'body'}); 97 | 98 | // Initialize clipboard: 99 | var clipboardBtnCopies = new ClipboardJS('[data-clipboard-copy]', { 100 | text: function(trigger) { 101 | return trigger.parentNode.textContent; 102 | } 103 | }); 104 | 105 | clipboardBtnCopies.on('success', function(e) { 106 | changeTooltipMessage(e.trigger, 'Copied!'); 107 | e.clearSelection(); 108 | }); 109 | 110 | clipboardBtnCopies.on('error', function() { 111 | changeTooltipMessage(e.trigger,'Press Ctrl+C or Command+C to copy'); 112 | }); 113 | }); 114 | } 115 | })(window.jQuery || window.$) 116 | -------------------------------------------------------------------------------- /docs/pkgdown.yml: -------------------------------------------------------------------------------- 1 | pandoc: 2.7.3 2 | pkgdown: 1.3.0 3 | pkgdown_sha: ~ 4 | articles: [] 5 | urls: 6 | reference: https://dapr.mikewk.com/reference 7 | article: https://dapr.mikewk.com/articles 8 | 9 | -------------------------------------------------------------------------------- /docs/reference/dap.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | dap: Data frame apply functions — dap • dapr 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 64 | 65 | 66 | 67 | 68 | 69 |
    70 |
    71 | 114 | 115 | 116 |
    117 | 118 |
    119 |
    120 | 125 | 126 |
    127 | 128 |

    Functions that apply expressions to input data objects and return data 129 | frames.

    130 |

    dapc: Apply function to columns of a data frame.

    131 |

    dapr: Apply function to rows of a data frame.

    132 |

    dapc_if: Apply function to certain columns of a data frame.

    133 |

    dapr_if: Apply function to certain rows of a data frame.

    134 | 135 |
    136 | 137 |
    dapc(.data, .f, ...)
    138 | 
    139 | dapr(.data, .f, ...)
    140 | 
    141 | dapc_if(.data, .predicate, .f, ...)
    142 | 
    143 | dapr_if(.data, .predicate, .f, ...)
    144 | 145 |

    Arguments

    146 | 147 | 148 | 149 | 150 | 151 | 152 | 153 | 154 | 159 | 160 | 161 | 162 | 163 | 164 | 165 | 166 | 176 | 177 |
    .data

    Data frame input.

    .f

    Function to apply to element (columns or rows). This can be written 155 | as a single function name e.g., mean, a formula-like function call 156 | where '.x' is assumed to be the iterated over element of input data e.g., 157 | ~ mean(.x), or an in-line function definition e.g., 158 | function(x) mean(x).

    ...

    Other values passed to function call.

    .predicate

    Logical vector or expression evaluating to a logical vector. 167 | If not a logical vector, this can be written as a single function name 168 | e.g., is.numeric, a formula-like function call where '.x' is assumed 169 | to be the iterated over element of input data e.g., 170 | ~ is.numeric(.x), or an in-line function definition e.g., 171 | function(x) is.numeric(x). Regardless, if a logical vector is not 172 | provided, this expression must return a logical vector of the same length 173 | as the input .data object.

    174 |

    The resulting logical vector is used to determine which elements (rows or 175 | columns) to iterate over with the .f function/expression.

    178 | 179 |

    Value

    180 | 181 |

    A data frame

    182 | 183 |

    See also

    184 | 185 | 186 | 187 | 188 |
    189 | 200 |
    201 | 202 | 211 |
    212 | 213 | 214 | 215 | 216 | 217 | 218 | -------------------------------------------------------------------------------- /docs/reference/figures/logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/docs/reference/figures/logo.png -------------------------------------------------------------------------------- /docs/reference/ilap.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | Iterator list apply — ilap • dapr 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 59 | 60 | 61 | 62 | 63 | 64 |
    65 |
    66 | 109 | 110 | 111 |
    112 | 113 |
    114 |
    115 | 120 | 121 |
    122 | 123 |

    ilap: Iterate over sequence length of input and return list(s)

    124 | 125 |
    126 | 127 |
    ilap(.data, .f, ...)
    128 | 129 |

    Arguments

    130 | 131 | 132 | 133 | 134 | 139 | 140 | 141 | 142 | 147 | 148 | 149 | 150 | 151 | 152 |
    .data

    Object representing the sequence length, used as ".i" in the .f 135 | expression. If matrix or data frame, sequence length will be determined by 136 | the number of columns. If integer, then it will be passed directly onto 137 | function call, otherwise the object will be converted into a sequence from 138 | 1 to the length of the object.

    .f

    Function to apply to each element (as an integer position) of input 143 | object. This can be written as a single function name e.g., mean, a 144 | formula-like function call where '.i' is assumed to be the integer position 145 | of input data object e.g., ~ mean(mtcars[[.i]]), or an in-line 146 | function definition e.g., function(x) mean(mtcars[[x]]).

    ...

    Other values passed to function call.

    153 | 154 |

    Value

    155 | 156 |

    A list

    157 | 158 |

    See also

    159 | 160 |

    Other lap: lap

    161 | 162 | 163 |

    Examples

    164 |
    165 | ## return string list 166 | ilap(1:10, ~ paste0(letters[.i], rev(LETTERS)[.i]))
    #> [[1]] 167 | #> [1] "aZ" 168 | #> 169 | #> [[2]] 170 | #> [1] "bY" 171 | #> 172 | #> [[3]] 173 | #> [1] "cX" 174 | #> 175 | #> [[4]] 176 | #> [1] "dW" 177 | #> 178 | #> [[5]] 179 | #> [1] "eV" 180 | #> 181 | #> [[6]] 182 | #> [1] "fU" 183 | #> 184 | #> [[7]] 185 | #> [1] "gT" 186 | #> 187 | #> [[8]] 188 | #> [1] "hS" 189 | #> 190 | #> [[9]] 191 | #> [1] "iR" 192 | #> 193 | #> [[10]] 194 | #> [1] "jQ" 195 | #>
    196 | ## return list of columns 197 | ilap(mtcars, ~ c(row.names(mtcars)[.i], mtcars$wt[.i]))
    #> [[1]] 198 | #> [1] "Mazda RX4" "2.62" 199 | #> 200 | #> [[2]] 201 | #> [1] "Mazda RX4 Wag" "2.875" 202 | #> 203 | #> [[3]] 204 | #> [1] "Datsun 710" "2.32" 205 | #> 206 | #> [[4]] 207 | #> [1] "Hornet 4 Drive" "3.215" 208 | #> 209 | #> [[5]] 210 | #> [1] "Hornet Sportabout" "3.44" 211 | #> 212 | #> [[6]] 213 | #> [1] "Valiant" "3.46" 214 | #> 215 | #> [[7]] 216 | #> [1] "Duster 360" "3.57" 217 | #> 218 | #> [[8]] 219 | #> [1] "Merc 240D" "3.19" 220 | #> 221 | #> [[9]] 222 | #> [1] "Merc 230" "3.15" 223 | #> 224 | #> [[10]] 225 | #> [1] "Merc 280" "3.44" 226 | #> 227 | #> [[11]] 228 | #> [1] "Merc 280C" "3.44" 229 | #>
    230 |
    231 |
    232 | 245 |
    246 | 247 | 256 |
    257 | 258 | 259 | 260 | 261 | 262 | 263 | -------------------------------------------------------------------------------- /docs/reference/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | Function reference • dapr 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 57 | 58 | 59 | 60 | 61 | 62 |
    63 |
    64 | 107 | 108 | 109 |
    110 | 111 |
    112 |
    113 | 116 | 117 | 118 | 119 | 120 | 121 | 122 | 123 | 124 | 125 | 126 | 127 | 131 | 132 | 133 | 134 | 137 | 138 | 139 | 140 | 143 | 144 | 145 | 146 | 149 | 150 | 151 | 152 | 155 | 156 | 157 | 158 | 161 | 162 | 163 | 164 | 167 | 168 | 169 | 170 |
    128 |

    All functions

    129 |

    130 |
    135 |

    dapc() dapr() dapc_if() dapr_if()

    136 |

    dap: Data frame apply functions

    141 |

    ilap()

    142 |

    Iterator list apply

    147 |

    lap() lapr() lapc() lap2()

    148 |

    lap: List apply functions

    153 |

    vap_dbl() vap_chr() vap_lgl() vap_int()

    154 |

    vap: Vector apply functions

    159 |

    vapc_chr() vapc_dbl() vapc_lgl() vapc_int()

    160 |

    vapr: Vector apply-to-column functions

    165 |

    vapr_chr() vapr_dbl() vapr_lgl() vapr_int()

    166 |

    vapr: Vector apply-to-row functions

    171 |
    172 | 173 | 179 |
    180 | 181 | 190 |
    191 | 192 | 193 | 194 | 195 | 196 | 197 | -------------------------------------------------------------------------------- /docs/reference/lap.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | lap: List apply functions — lap • dapr 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 62 | 63 | 64 | 65 | 66 | 67 |
    68 |
    69 | 112 | 113 | 114 |
    115 | 116 |
    117 |
    118 | 123 | 124 |
    125 | 126 |

    Function(s) that apply expressions to input data objects and return lists.

    127 |

    lap: Iterate over input and return list(s)

    128 |

    lapr: Iterate over input rows and return list(s)

    129 |

    lapr: Iterate over input columbs and return list(s)

    130 | 131 |
    132 | 133 |
    lap(.data, .f, ...)
    134 | 
    135 | lapr(.data, .f, ...)
    136 | 
    137 | lapc(.data, .f, ...)
    138 | 
    139 | lap2(.x, .y, .f, ...)
    140 | 141 |

    Arguments

    142 | 143 | 144 | 145 | 146 | 149 | 150 | 151 | 152 | 157 | 158 | 159 | 160 | 161 | 162 | 163 | 164 | 165 | 166 | 167 | 168 | 169 | 170 |
    .data

    Input object–numeric, character, list, data frame, etc.–over 147 | which elements will be iterated. If matrix or data frame, each 148 | column will be treated as the elements which are to be iterated over.

    .f

    Function to apply to each element of input object. This can be 153 | written as a single function name e.g., mean, a formula-like 154 | function call where '.x' is assumed to be the iterated over element of 155 | input data e.g., ~ mean(.x), or an in-line function definition e.g., 156 | function(x) mean(x).

    ...

    Other values passed to function call.

    .x

    First data vector input (for lap2)

    .y

    Second data vector input (for lap2)

    171 | 172 |

    Value

    173 | 174 |

    A list

    175 | 176 |

    See also

    177 | 178 |

    dap vap

    179 |

    Other lap: ilap

    180 | 181 | 182 |

    Examples

    183 |
    184 | ## return string list 185 | lap(letters, ~ paste0(.x, "."))
    #> [[1]] 186 | #> [1] "a." 187 | #> 188 | #> [[2]] 189 | #> [1] "b." 190 | #> 191 | #> [[3]] 192 | #> [1] "c." 193 | #> 194 | #> [[4]] 195 | #> [1] "d." 196 | #> 197 | #> [[5]] 198 | #> [1] "e." 199 | #> 200 | #> [[6]] 201 | #> [1] "f." 202 | #> 203 | #> [[7]] 204 | #> [1] "g." 205 | #> 206 | #> [[8]] 207 | #> [1] "h." 208 | #> 209 | #> [[9]] 210 | #> [1] "i." 211 | #> 212 | #> [[10]] 213 | #> [1] "j." 214 | #> 215 | #> [[11]] 216 | #> [1] "k." 217 | #> 218 | #> [[12]] 219 | #> [1] "l." 220 | #> 221 | #> [[13]] 222 | #> [1] "m." 223 | #> 224 | #> [[14]] 225 | #> [1] "n." 226 | #> 227 | #> [[15]] 228 | #> [1] "o." 229 | #> 230 | #> [[16]] 231 | #> [1] "p." 232 | #> 233 | #> [[17]] 234 | #> [1] "q." 235 | #> 236 | #> [[18]] 237 | #> [1] "r." 238 | #> 239 | #> [[19]] 240 | #> [1] "s." 241 | #> 242 | #> [[20]] 243 | #> [1] "t." 244 | #> 245 | #> [[21]] 246 | #> [1] "u." 247 | #> 248 | #> [[22]] 249 | #> [1] "v." 250 | #> 251 | #> [[23]] 252 | #> [1] "w." 253 | #> 254 | #> [[24]] 255 | #> [1] "x." 256 | #> 257 | #> [[25]] 258 | #> [1] "y." 259 | #> 260 | #> [[26]] 261 | #> [1] "z." 262 | #>
    263 | ## return list of columns 264 | lap(mtcars[1:5, ], as.character)
    #> $mpg 265 | #> [1] "21" "21" "22.8" "21.4" "18.7" 266 | #> 267 | #> $cyl 268 | #> [1] "6" "6" "4" "6" "8" 269 | #> 270 | #> $disp 271 | #> [1] "160" "160" "108" "258" "360" 272 | #> 273 | #> $hp 274 | #> [1] "110" "110" "93" "110" "175" 275 | #> 276 | #> $drat 277 | #> [1] "3.9" "3.9" "3.85" "3.08" "3.15" 278 | #> 279 | #> $wt 280 | #> [1] "2.62" "2.875" "2.32" "3.215" "3.44" 281 | #> 282 | #> $qsec 283 | #> [1] "16.46" "17.02" "18.61" "19.44" "17.02" 284 | #> 285 | #> $vs 286 | #> [1] "0" "0" "1" "1" "0" 287 | #> 288 | #> $am 289 | #> [1] "1" "1" "1" "0" "0" 290 | #> 291 | #> $gear 292 | #> [1] "4" "4" "4" "3" "3" 293 | #> 294 | #> $carb 295 | #> [1] "4" "4" "1" "1" "2" 296 | #>
    297 | ## map over two vectors 298 | lap2(letters, LETTERS, ~ paste0(.x, .y, .x, .y))
    #> [[1]] 299 | #> [1] "aAaA" 300 | #> 301 | #> [[2]] 302 | #> [1] "bBbB" 303 | #> 304 | #> [[3]] 305 | #> [1] "cCcC" 306 | #> 307 | #> [[4]] 308 | #> [1] "dDdD" 309 | #> 310 | #> [[5]] 311 | #> [1] "eEeE" 312 | #> 313 | #> [[6]] 314 | #> [1] "fFfF" 315 | #> 316 | #> [[7]] 317 | #> [1] "gGgG" 318 | #> 319 | #> [[8]] 320 | #> [1] "hHhH" 321 | #> 322 | #> [[9]] 323 | #> [1] "iIiI" 324 | #> 325 | #> [[10]] 326 | #> [1] "jJjJ" 327 | #> 328 | #> [[11]] 329 | #> [1] "kKkK" 330 | #> 331 | #> [[12]] 332 | #> [1] "lLlL" 333 | #> 334 | #> [[13]] 335 | #> [1] "mMmM" 336 | #> 337 | #> [[14]] 338 | #> [1] "nNnN" 339 | #> 340 | #> [[15]] 341 | #> [1] "oOoO" 342 | #> 343 | #> [[16]] 344 | #> [1] "pPpP" 345 | #> 346 | #> [[17]] 347 | #> [1] "qQqQ" 348 | #> 349 | #> [[18]] 350 | #> [1] "rRrR" 351 | #> 352 | #> [[19]] 353 | #> [1] "sSsS" 354 | #> 355 | #> [[20]] 356 | #> [1] "tTtT" 357 | #> 358 | #> [[21]] 359 | #> [1] "uUuU" 360 | #> 361 | #> [[22]] 362 | #> [1] "vVvV" 363 | #> 364 | #> [[23]] 365 | #> [1] "wWwW" 366 | #> 367 | #> [[24]] 368 | #> [1] "xXxX" 369 | #> 370 | #> [[25]] 371 | #> [1] "yYyY" 372 | #> 373 | #> [[26]] 374 | #> [1] "zZzZ" 375 | #>
    376 |
    377 |
    378 | 391 |
    392 | 393 | 402 |
    403 | 404 | 405 | 406 | 407 | 408 | 409 | -------------------------------------------------------------------------------- /docs/reference/vap.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | vap: Vector apply functions — vap • dapr 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 64 | 65 | 66 | 67 | 68 | 69 |
    70 |
    71 | 114 | 115 | 116 |
    117 | 118 |
    119 |
    120 | 125 | 126 |
    127 | 128 |

    Functions that apply expressions to input objects and return atomic vectors 129 | e.g., numeric (double), integer, character, logical.

    130 |

    vap_dbl: Iterate over input and return double(s)

    131 |

    vap_chr: Iterate over input and return character(s)

    132 |

    vap_lgl: Iterate over input and return logical(s)

    133 |

    vap_int: Iterate over input and return integer(s)

    134 | 135 |
    136 | 137 |
    vap_dbl(.data, .f, ...)
    138 | 
    139 | vap_chr(.data, .f, ...)
    140 | 
    141 | vap_lgl(.data, .f, ...)
    142 | 
    143 | vap_int(.data, .f, ...)
    144 | 145 |

    Arguments

    146 | 147 | 148 | 149 | 150 | 153 | 154 | 155 | 156 | 165 | 166 | 167 | 168 | 169 | 170 |
    .data

    Input object–numeric, character, list, data frame, etc.–over 151 | which elements will be iterated. If matrix or data frame, each 152 | column will be treated as an element.

    .f

    Action to apply to each element of .data. The action can be 157 | articulated in one of the four following ways:

      158 |
    1. supplying a function object (e.g., mean)

    2. 159 |
    3. defining a function (in-line; e.g., function(x) mean(x))

    4. 160 |
    5. specifying a formula-like call where '.x' is assumed to be the iterated 161 | over element of .data (e.g., ~ mean(.x))

    6. 162 |
    7. providing a name or position of .data to return (e.g., 163 | 1, "varname", etc.)

    8. 164 |
    ...

    Other values passed to function call.

    171 | 172 |

    Value

    173 | 174 |

    A double vector

    175 |

    A character vector

    176 |

    A logical vector

    177 |

    An integer vector

    178 | 179 |

    See also

    180 | 181 |

    lap dap

    182 |

    Other vap: vapc, vapr

    183 | 184 | 185 |

    Examples

    186 |
    187 | ## character 188 | vap_chr(letters, ~ paste0(.x, "."))
    #> a b c d e f g h i j k l m n o p 189 | #> "a." "b." "c." "d." "e." "f." "g." "h." "i." "j." "k." "l." "m." "n." "o." "p." 190 | #> q r s t u v w x y z 191 | #> "q." "r." "s." "t." "u." "v." "w." "x." "y." "z."
    192 | ## double 193 | vap_dbl(rnorm(4), round, 3)
    #> [1] -1.400 0.255 -2.437 -0.006
    194 | ## logical 195 | vap_lgl(letters, ~ .x %in% c("a", "e", "i", "o", "u"))
    #> a b c d e f g h i j k l m 196 | #> TRUE FALSE FALSE FALSE TRUE FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE 197 | #> n o p q r s t u v w x y z 198 | #> FALSE TRUE FALSE FALSE FALSE FALSE FALSE TRUE FALSE FALSE FALSE FALSE FALSE
    199 | ## integer 200 | vap_int(as.data.frame(replicate(10, sample(1:10))), 8)
    #> [1] 9 4 5 8 2 6 7 3 1 10
    201 |
    202 |
    203 | 216 |
    217 | 218 | 227 |
    228 | 229 | 230 | 231 | 232 | 233 | 234 | -------------------------------------------------------------------------------- /docs/reference/vapc.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | vapr: Vector apply-to-column functions — vapc • dapr 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 64 | 65 | 66 | 67 | 68 | 69 |
    70 |
    71 | 114 | 115 | 116 |
    117 | 118 |
    119 |
    120 | 125 | 126 |
    127 | 128 |

    Functions that apply expressions to the columns of input objects and return 129 | atomic vectors e.g., numeric (double), integer, character, logical.

    130 |

    vapc_chr: Iterate over input columns and return character(s)

    131 |

    vapc_dbl: Iterate over input columns and return numeric(s)

    132 |

    vapc_lgl: Iterate over input columns and return logical(s)

    133 |

    vapc_int: Iterate over input columns and return integer(s)

    134 | 135 |
    136 | 137 |
    vapc_chr(.data, .f, ...)
    138 | 
    139 | vapc_dbl(.data, .f, ...)
    140 | 
    141 | vapc_lgl(.data, .f, ...)
    142 | 
    143 | vapc_int(.data, .f, ...)
    144 | 145 |

    Arguments

    146 | 147 | 148 | 149 | 150 | 152 | 153 | 154 | 155 | 164 | 165 | 166 | 167 | 168 | 169 |
    .data

    Input object–must be two-dimensional (e.g., matrix, data.frame) 151 | –over which the second dimension (columns) will be iterated

    .f

    Action to apply to each element of .data. The action can be 156 | articulated in one of the four following ways:

      157 |
    1. supplying a function object (e.g., mean)

    2. 158 |
    3. defining a function (in-line; e.g., function(x) mean(x))

    4. 159 |
    5. specifying a formula-like call where '.x' is assumed to be the iterated 160 | over element of .data (e.g., ~ mean(.x))

    6. 161 |
    7. providing a name or position of .data to return (e.g., 162 | 1, "varname", etc.)

    8. 163 |
    ...

    Other values passed to function call.

    170 | 171 |

    Value

    172 | 173 |

    A character vector

    174 |

    A numeric vector

    175 |

    A logical vector

    176 |

    An integer vector

    177 | 178 |

    See also

    179 | 180 |

    lap dap

    181 |

    Other vap: vapr, vap

    182 | 183 | 184 |
    185 | 196 |
    197 | 198 | 207 |
    208 | 209 | 210 | 211 | 212 | 213 | 214 | -------------------------------------------------------------------------------- /docs/reference/vapr.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | vapr: Vector apply-to-row functions — vapr • dapr 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 64 | 65 | 66 | 67 | 68 | 69 |
    70 |
    71 | 114 | 115 | 116 |
    117 | 118 |
    119 |
    120 | 125 | 126 |
    127 | 128 |

    Functions that apply expressions to the rows of input objects and return 129 | atomic vectors e.g., numeric (double), integer, character, logical.

    130 |

    vapr_chr: Iterate over input rows and return character(s)

    131 |

    vapr_dbl: Iterate over input rows and return numeric(s)

    132 |

    vapr_lgl: Iterate over input rows and return logical(s)

    133 |

    vapr_int: Iterate over input rows and return integer(s)

    134 | 135 |
    136 | 137 |
    vapr_chr(.data, .f, ...)
    138 | 
    139 | vapr_dbl(.data, .f, ...)
    140 | 
    141 | vapr_lgl(.data, .f, ...)
    142 | 
    143 | vapr_int(.data, .f, ...)
    144 | 145 |

    Arguments

    146 | 147 | 148 | 149 | 150 | 152 | 153 | 154 | 155 | 164 | 165 | 166 | 167 | 168 | 169 |
    .data

    Input object–must be two-dimensional (e.g., matrix, data.frame) 151 | –over which the first dimension (rows) will be iterated

    .f

    Action to apply to each element of .data. The action can be 156 | articulated in one of the four following ways:

      157 |
    1. supplying a function object (e.g., mean)

    2. 158 |
    3. defining a function (in-line; e.g., function(x) mean(x))

    4. 159 |
    5. specifying a formula-like call where '.x' is assumed to be the iterated 160 | over element of .data (e.g., ~ mean(.x))

    6. 161 |
    7. providing a name or position of .data to return (e.g., 162 | 1, "varname", etc.)

    8. 163 |
    ...

    Other values passed to function call.

    170 | 171 |

    Value

    172 | 173 |

    A character vector

    174 |

    A numeric vector

    175 |

    A logical vector

    176 |

    An integer vector

    177 | 178 |

    See also

    179 | 180 |

    lap dap

    181 |

    Other vap: vapc, vap

    182 | 183 | 184 |
    185 | 196 |
    197 | 198 | 207 |
    208 | 209 | 210 | 211 | 212 | 213 | 214 | -------------------------------------------------------------------------------- /docs/sitemap.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | https://dapr.mikewk.com/index.html 5 | 6 | 7 | https://dapr.mikewk.com/reference/dap.html 8 | 9 | 10 | https://dapr.mikewk.com/reference/ilap.html 11 | 12 | 13 | https://dapr.mikewk.com/reference/lap.html 14 | 15 | 16 | https://dapr.mikewk.com/reference/vap.html 17 | 18 | 19 | https://dapr.mikewk.com/reference/vapc.html 20 | 21 | 22 | https://dapr.mikewk.com/reference/vapr.html 23 | 24 | 25 | -------------------------------------------------------------------------------- /docs/tools/readme/benchmark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/docs/tools/readme/benchmark.png -------------------------------------------------------------------------------- /man/dap.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/dap.R 3 | \name{dap} 4 | \alias{dap} 5 | \alias{dapc} 6 | \alias{dapr} 7 | \alias{dapc_if} 8 | \alias{dapr_if} 9 | \title{dap: Data frame apply functions} 10 | \usage{ 11 | dapc(.data, .f, ...) 12 | 13 | dapr(.data, .f, ...) 14 | 15 | dapc_if(.data, .predicate, .f, ...) 16 | 17 | dapr_if(.data, .predicate, .f, ...) 18 | } 19 | \arguments{ 20 | \item{.data}{Data frame input.} 21 | 22 | \item{.f}{Function to apply to element (columns or rows). This can be written 23 | as a single function name e.g., \code{mean}, a formula-like function call 24 | where '.x' is assumed to be the iterated over element of input data e.g., 25 | \code{~ mean(.x)}, or an in-line function definition e.g., 26 | \code{function(x) mean(x)}.} 27 | 28 | \item{...}{Other values passed to function call.} 29 | 30 | \item{.predicate}{Logical vector or expression evaluating to a logical vector. 31 | If not a logical vector, this can be written as a single function name 32 | e.g., \code{is.numeric}, a formula-like function call where '.x' is assumed 33 | to be the iterated over element of input data e.g., 34 | \code{~ is.numeric(.x)}, or an in-line function definition e.g., 35 | \code{function(x) is.numeric(x)}. Regardless, if a logical vector is not 36 | provided, this expression must return a logical vector of the same length 37 | as the input .data object. 38 | 39 | The resulting logical vector is used to determine which elements (rows or 40 | columns) to iterate over with the .f function/expression.} 41 | } 42 | \value{ 43 | A data frame 44 | } 45 | \description{ 46 | Functions that apply expressions to input data objects and return data 47 | frames. 48 | 49 | dapc: Apply function to columns of a data frame. 50 | 51 | dapr: Apply function to rows of a data frame. 52 | 53 | dapc_if: Apply function to certain columns of a data frame. 54 | 55 | dapr_if: Apply function to certain rows of a data frame. 56 | } 57 | \seealso{ 58 | \code{\link{lap}} \code{\link{vap}} 59 | } 60 | \concept{dap} 61 | -------------------------------------------------------------------------------- /man/figures/logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/man/figures/logo.png -------------------------------------------------------------------------------- /man/ilap.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/ilap.R 3 | \name{ilap} 4 | \alias{ilap} 5 | \title{Iterator list apply} 6 | \usage{ 7 | ilap(.data, .f, ...) 8 | } 9 | \arguments{ 10 | \item{.data}{Object representing the sequence length, used as ".i" in the .f 11 | expression. If matrix or data frame, sequence length will be determined by 12 | the number of columns. If integer, then it will be passed directly onto 13 | function call, otherwise the object will be converted into a sequence from 14 | 1 to the length of the object.} 15 | 16 | \item{.f}{Function to apply to each element (as an integer position) of input 17 | object. This can be written as a single function name e.g., \code{mean}, a 18 | formula-like function call where '.i' is assumed to be the integer position 19 | of input data object e.g., \code{~ mean(mtcars[[.i]])}, or an in-line 20 | function definition e.g., \code{function(x) mean(mtcars[[x]])}.} 21 | 22 | \item{...}{Other values passed to function call.} 23 | } 24 | \value{ 25 | A list 26 | } 27 | \description{ 28 | ilap: Iterate over sequence length of input and return list(s) 29 | } 30 | \examples{ 31 | 32 | ## return string list 33 | ilap(1:10, ~ paste0(letters[.i], rev(LETTERS)[.i])) 34 | 35 | ## return list of columns 36 | ilap(mtcars, ~ c(row.names(mtcars)[.i], mtcars$wt[.i])) 37 | 38 | } 39 | \seealso{ 40 | Other lap: \code{\link{lap}} 41 | } 42 | \concept{lap} 43 | -------------------------------------------------------------------------------- /man/lap.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/lap.R 3 | \name{lap} 4 | \alias{lap} 5 | \alias{lapr} 6 | \alias{lapc} 7 | \alias{lap2} 8 | \title{lap: List apply functions} 9 | \usage{ 10 | lap(.data, .f, ...) 11 | 12 | lapr(.data, .f, ...) 13 | 14 | lapc(.data, .f, ...) 15 | 16 | lap2(.x, .y, .f, ...) 17 | } 18 | \arguments{ 19 | \item{.data}{Input object–numeric, character, list, data frame, etc.–over 20 | which elements will be iterated. If matrix or data frame, each 21 | column will be treated as the elements which are to be iterated over.} 22 | 23 | \item{.f}{Function to apply to each element of input object. This can be 24 | written as a single function name e.g., \code{mean}, a formula-like 25 | function call where '.x' is assumed to be the iterated over element of 26 | input data e.g., \code{~ mean(.x)}, or an in-line function definition e.g., 27 | \code{function(x) mean(x)}.} 28 | 29 | \item{...}{Other values passed to function call.} 30 | 31 | \item{.x}{First data vector input (for lap2)} 32 | 33 | \item{.y}{Second data vector input (for lap2)} 34 | } 35 | \value{ 36 | A list 37 | } 38 | \description{ 39 | Function(s) that apply expressions to input data objects and return lists. 40 | 41 | lap: Iterate over input and return list(s) 42 | 43 | lapr: Iterate over input rows and return list(s) 44 | 45 | lapr: Iterate over input columbs and return list(s) 46 | } 47 | \examples{ 48 | 49 | ## return string list 50 | lap(letters, ~ paste0(.x, ".")) 51 | 52 | ## return list of columns 53 | lap(mtcars[1:5, ], as.character) 54 | 55 | ## map over two vectors 56 | lap2(letters, LETTERS, ~ paste0(.x, .y, .x, .y)) 57 | 58 | } 59 | \seealso{ 60 | \code{\link{dap}} \code{\link{vap}} 61 | 62 | Other lap: \code{\link{ilap}} 63 | } 64 | \concept{lap} 65 | -------------------------------------------------------------------------------- /man/vap.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/vap.R 3 | \name{vap} 4 | \alias{vap} 5 | \alias{vap_dbl} 6 | \alias{vap_chr} 7 | \alias{vap_lgl} 8 | \alias{vap_int} 9 | \title{vap: Vector apply functions} 10 | \usage{ 11 | vap_dbl(.data, .f, ...) 12 | 13 | vap_chr(.data, .f, ...) 14 | 15 | vap_lgl(.data, .f, ...) 16 | 17 | vap_int(.data, .f, ...) 18 | } 19 | \arguments{ 20 | \item{.data}{Input object–numeric, character, list, data frame, etc.–over 21 | which elements will be iterated. If matrix or data frame, each 22 | column will be treated as an element.} 23 | 24 | \item{.f}{Action to apply to each element of \code{.data}. The action can be 25 | articulated in one of the four following ways: 26 | \enumerate{ 27 | \item supplying a function object (e.g., \code{mean}) 28 | \item defining a function (in-line; e.g., \code{function(x) mean(x)}) 29 | \item specifying a formula-like call where '.x' is assumed to be the iterated 30 | over element of \code{.data} (e.g., \code{~ mean(.x)}) 31 | \item providing a name or position of \code{.data} to return (e.g., 32 | \code{1}, \code{"varname"}, etc.) 33 | }} 34 | 35 | \item{...}{Other values passed to function call.} 36 | } 37 | \value{ 38 | A double vector 39 | 40 | A character vector 41 | 42 | A logical vector 43 | 44 | An integer vector 45 | } 46 | \description{ 47 | Functions that apply expressions to input objects and return atomic vectors 48 | e.g., numeric (double), integer, character, logical. 49 | 50 | vap_dbl: Iterate over input and return double(s) 51 | 52 | vap_chr: Iterate over input and return character(s) 53 | 54 | vap_lgl: Iterate over input and return logical(s) 55 | 56 | vap_int: Iterate over input and return integer(s) 57 | } 58 | \examples{ 59 | 60 | ## character 61 | vap_chr(letters, ~ paste0(.x, ".")) 62 | 63 | ## double 64 | vap_dbl(rnorm(4), round, 3) 65 | 66 | ## logical 67 | vap_lgl(letters, ~ .x \%in\% c("a", "e", "i", "o", "u")) 68 | 69 | ## integer 70 | vap_int(as.data.frame(replicate(10, sample(1:10))), 8) 71 | 72 | } 73 | \seealso{ 74 | \code{\link{lap}} \code{\link{dap}} 75 | 76 | Other vap: \code{\link{vapc}}, \code{\link{vapr}} 77 | } 78 | \concept{vap} 79 | -------------------------------------------------------------------------------- /man/vapc.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/vapc.R 3 | \name{vapc} 4 | \alias{vapc} 5 | \alias{vapc_chr} 6 | \alias{vapc_dbl} 7 | \alias{vapc_lgl} 8 | \alias{vapc_int} 9 | \title{vapr: Vector apply-to-column functions} 10 | \usage{ 11 | vapc_chr(.data, .f, ...) 12 | 13 | vapc_dbl(.data, .f, ...) 14 | 15 | vapc_lgl(.data, .f, ...) 16 | 17 | vapc_int(.data, .f, ...) 18 | } 19 | \arguments{ 20 | \item{.data}{Input object–must be two-dimensional (e.g., matrix, data.frame) 21 | –over which the second dimension (columns) will be iterated} 22 | 23 | \item{.f}{Action to apply to each element of \code{.data}. The action can be 24 | articulated in one of the four following ways: 25 | \enumerate{ 26 | \item supplying a function object (e.g., \code{mean}) 27 | \item defining a function (in-line; e.g., \code{function(x) mean(x)}) 28 | \item specifying a formula-like call where '.x' is assumed to be the iterated 29 | over element of \code{.data} (e.g., \code{~ mean(.x)}) 30 | \item providing a name or position of \code{.data} to return (e.g., 31 | \code{1}, \code{"varname"}, etc.) 32 | }} 33 | 34 | \item{...}{Other values passed to function call.} 35 | } 36 | \value{ 37 | A character vector 38 | 39 | A numeric vector 40 | 41 | A logical vector 42 | 43 | An integer vector 44 | } 45 | \description{ 46 | Functions that apply expressions to the columns of input objects and return 47 | atomic vectors e.g., numeric (double), integer, character, logical. 48 | 49 | vapc_chr: Iterate over input \strong{columns} and return \strong{character(s)} 50 | 51 | vapc_dbl: Iterate over input \strong{columns} and return \strong{numeric(s)} 52 | 53 | vapc_lgl: Iterate over input \strong{columns} and return \strong{logical(s)} 54 | 55 | vapc_int: Iterate over input \strong{columns} and return \strong{integer(s)} 56 | } 57 | \seealso{ 58 | \code{\link{lap}} \code{\link{dap}} 59 | 60 | Other vap: \code{\link{vapr}}, \code{\link{vap}} 61 | } 62 | \concept{vap} 63 | -------------------------------------------------------------------------------- /man/vapr.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/vapr.R 3 | \name{vapr} 4 | \alias{vapr} 5 | \alias{vapr_chr} 6 | \alias{vapr_dbl} 7 | \alias{vapr_lgl} 8 | \alias{vapr_int} 9 | \title{vapr: Vector apply-to-row functions} 10 | \usage{ 11 | vapr_chr(.data, .f, ...) 12 | 13 | vapr_dbl(.data, .f, ...) 14 | 15 | vapr_lgl(.data, .f, ...) 16 | 17 | vapr_int(.data, .f, ...) 18 | } 19 | \arguments{ 20 | \item{.data}{Input object–must be two-dimensional (e.g., matrix, data.frame) 21 | –over which the first dimension (rows) will be iterated} 22 | 23 | \item{.f}{Action to apply to each element of \code{.data}. The action can be 24 | articulated in one of the four following ways: 25 | \enumerate{ 26 | \item supplying a function object (e.g., \code{mean}) 27 | \item defining a function (in-line; e.g., \code{function(x) mean(x)}) 28 | \item specifying a formula-like call where '.x' is assumed to be the iterated 29 | over element of \code{.data} (e.g., \code{~ mean(.x)}) 30 | \item providing a name or position of \code{.data} to return (e.g., 31 | \code{1}, \code{"varname"}, etc.) 32 | }} 33 | 34 | \item{...}{Other values passed to function call.} 35 | } 36 | \value{ 37 | A character vector 38 | 39 | A numeric vector 40 | 41 | A logical vector 42 | 43 | An integer vector 44 | } 45 | \description{ 46 | Functions that apply expressions to the rows of input objects and return 47 | atomic vectors e.g., numeric (double), integer, character, logical. 48 | 49 | vapr_chr: Iterate over input \strong{rows} and return \strong{character(s)} 50 | 51 | vapr_dbl: Iterate over input \strong{rows} and return \strong{numeric(s)} 52 | 53 | vapr_lgl: Iterate over input \strong{rows} and return \strong{logical(s)} 54 | 55 | vapr_int: Iterate over input \strong{rows} and return \strong{integer(s)} 56 | } 57 | \seealso{ 58 | \code{\link{lap}} \code{\link{dap}} 59 | 60 | Other vap: \code{\link{vapc}}, \code{\link{vap}} 61 | } 62 | \concept{vap} 63 | -------------------------------------------------------------------------------- /pkgdown/extra.css: -------------------------------------------------------------------------------- 1 | 2 | @import url("https://fonts.googleapis.com/css?family=Roboto:400,400i,700,700i,900"); 3 | 4 | @import url(https://cdn.rawgit.com/tonsky/FiraCode/1.205/distr/fira_code.css); 5 | 6 | body { 7 | font-family: Roboto, sans-serif; 8 | font-size: 16px; 9 | line-height: 1.5; 10 | font-weight: 400; 11 | margin: .5em auto 5em auto; 12 | } 13 | 14 | h1, h2, h3, h4, .h1, .h2, .h3, .h4 { 15 | font-family: Roboto, sans-serif; 16 | font-weight: 900; 17 | } 18 | 19 | h1 {font-size: 2.1em} 20 | h2 {font-size: 1.8em} 21 | h3 {font-size: 1.6em} 22 | h4 {font-size: 1.3em} 23 | 24 | code { 25 | font-family: "Fira Code", Consolas, Monaco, Menlo, Inconsolata, monospace; 26 | } 27 | 28 | pre { 29 | box-shadow: 30 | rgba(0, 0, 0, 0.1) 0 2px 3px 1px, 31 | rgba(0, 0, 0, 0.1) 0 1px 3px 1px, 32 | rgba(0, 0, 0, 0.2) 0 1px 1px -1px; 33 | font-size: .80em; 34 | margin-left: auto; 35 | width: 98%; 36 | margin-right: auto; 37 | line-height: 1.4em; 38 | font-family: "Fira Code", Consolas, Monaco, Menlo, Inconsolata, monospace; 39 | } 40 | 41 | div.sourceCode { 42 | overflow: visible; 43 | } 44 | 45 | pre.sourceCode { 46 | margin-left: auto; 47 | margin-right: auto; 48 | } 49 | 50 | p { 51 | margin: 1.5em 0; 52 | } 53 | 54 | strong { 55 | font-family: Roboto, sans-serif; 56 | font-weight: 900; 57 | } 58 | 59 | strong code { 60 | font-family: "Fira Code", Consolas, Monaco, Menlo, Inconsolata, monospace; 61 | font-weight: 700; 62 | } 63 | 64 | code span.co, .co { 65 | color: #828f96; 66 | } 67 | 68 | code span.ot, .ot { 69 | color: #ddaa00; 70 | } 71 | 72 | .navbar-default { 73 | box-shadow: 74 | rgba(0, 0, 0, 0.1) 0 2px 3px 1px, 75 | rgba(0, 0, 0, 0.1) 0 1px 3px 1px, 76 | rgba(0, 0, 0, 0.2) 0 1px 1px -1px; 77 | background-color: #f3f3f3; 78 | border-color: #eee; 79 | } 80 | -------------------------------------------------------------------------------- /pkgdown/favicon/apple-touch-icon-120x120.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/pkgdown/favicon/apple-touch-icon-120x120.png -------------------------------------------------------------------------------- /pkgdown/favicon/apple-touch-icon-152x152.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/pkgdown/favicon/apple-touch-icon-152x152.png -------------------------------------------------------------------------------- /pkgdown/favicon/apple-touch-icon-180x180.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/pkgdown/favicon/apple-touch-icon-180x180.png -------------------------------------------------------------------------------- /pkgdown/favicon/apple-touch-icon-60x60.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/pkgdown/favicon/apple-touch-icon-60x60.png -------------------------------------------------------------------------------- /pkgdown/favicon/apple-touch-icon-76x76.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/pkgdown/favicon/apple-touch-icon-76x76.png -------------------------------------------------------------------------------- /pkgdown/favicon/apple-touch-icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/pkgdown/favicon/apple-touch-icon.png -------------------------------------------------------------------------------- /pkgdown/favicon/favicon-16x16.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/pkgdown/favicon/favicon-16x16.png -------------------------------------------------------------------------------- /pkgdown/favicon/favicon-32x32.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/pkgdown/favicon/favicon-32x32.png -------------------------------------------------------------------------------- /pkgdown/favicon/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/pkgdown/favicon/favicon.ico -------------------------------------------------------------------------------- /tests/testthat.R: -------------------------------------------------------------------------------- 1 | library(testthat) 2 | library(dapr) 3 | 4 | test_check("dapr") 5 | -------------------------------------------------------------------------------- /tests/testthat/test-dap.R: -------------------------------------------------------------------------------- 1 | context("test-dap") 2 | 3 | test_that("data frame apply functions", { 4 | d <- data.frame( 5 | a = letters[1:5], 6 | b = rnorm(5), 7 | c = rnorm(5), 8 | stringsAsFactors = FALSE 9 | ) 10 | ## columns 11 | expect_true(is.data.frame(dapc(d[-1], ~ round(.x, 3)))) 12 | expect_true(is.data.frame(dapc(d[-1], round, 3))) 13 | ## rows 14 | expect_true(is.data.frame(dapr(d[-1], ~ round(.x, 3)))) 15 | expect_true(is.data.frame(dapr(d[-1], round, 3))) 16 | ## columns IF 17 | expect_true(is.data.frame(dapc_if(d, is.numeric, ~ round(.x, 3)))) 18 | expect_true(is.data.frame(dapc_if(d, is.numeric, round, 3))) 19 | ## rows IF 20 | expect_true(is.data.frame( 21 | dapr_if(d[-1], c(TRUE, TRUE, FALSE, FALSE, TRUE), round))) 22 | expect_true(is.data.frame( 23 | dapr_if(d[-1], ~ sum(.x) > 0, ~ round(.x, 0)))) 24 | }) 25 | -------------------------------------------------------------------------------- /tests/testthat/test-lap.R: -------------------------------------------------------------------------------- 1 | context("test-lap") 2 | 3 | test_that("list apply functions", { 4 | d <- data.frame( 5 | a = letters[1:5], 6 | b = rnorm(5), 7 | c = rnorm(5), 8 | stringsAsFactors = FALSE 9 | ) 10 | expect_true(is.list(lap(d[-1], ~ round(.x, 3)))) 11 | expect_true(is.list(lap(d[-1], round, 3))) 12 | min <- 3 13 | expect_true(is.list(lap(d[-1], ~ round(.x, min)))) 14 | expect_true(is.list(lap(d[-1], round, digits = 3))) 15 | expect_true(is.list(lapr(d, paste))) 16 | expect_equal(length(lapr(d, paste)), nrow(d)) 17 | expect_equal(length(lapc(d, paste)), ncol(d)) 18 | 19 | expect_true(is.list(ilap(1:10, ~ paste0(letters[.i], rev(LETTERS)[.i])))) 20 | expect_equal(nchar(ilap(1:10, ~ paste0(letters[.i], rev(LETTERS)[.i]))[[1]]), 2) 21 | }) 22 | -------------------------------------------------------------------------------- /tests/testthat/test-lap2.R: -------------------------------------------------------------------------------- 1 | test_that("lap2 works", { 2 | expect_true( 3 | is.list(lap2(letters, LETTERS, paste0)) 4 | ) 5 | expect_equal( 6 | lap2(letters, LETTERS, paste0)[[1]], 7 | "aA" 8 | ) 9 | expect_true( 10 | is.list(lap2(letters, LETTERS, ~ paste0(.x, .y, .x, .y))) 11 | ) 12 | expect_equal( 13 | length(lap2(letters, LETTERS, ~ paste0(.x, .y, .x, .y))), 14 | 26L 15 | ) 16 | expect_equal( 17 | lap2(letters, LETTERS, ~ paste0(.x, .y, .x, .y))[[1]], 18 | "aAaA" 19 | ) 20 | }) 21 | -------------------------------------------------------------------------------- /tests/testthat/test-purrr-map.R: -------------------------------------------------------------------------------- 1 | context("map") 2 | 3 | test_that("preserves names", { 4 | out <- lap(list(x = 1, y = 2), identity) 5 | expect_equal(names(out), c("x", "y")) 6 | }) 7 | 8 | test_that("creates simple call", { 9 | out <- lap(1, function(x) sys.call())[[1]] 10 | expect_equal(out, quote(FUN(X[[i]], ...))) 11 | }) 12 | 13 | test_that("fails on non-vectors", { 14 | expect_error(lap(environment(), identity), "is_vector.*is not TRUE") 15 | expect_error(lap(quote(a), identity), "is_vector.*is not TRUE") 16 | }) 17 | 18 | test_that("0 length input gives 0 length output", { 19 | out1 <- lap(list(), identity) 20 | expect_equal(out1, list()) 21 | 22 | out2 <- lap(NULL, identity) 23 | expect_equal(out2, list()) 24 | }) 25 | 26 | test_that("lap() always returns a list", { 27 | expect_is(lap(mtcars, mean), "list") 28 | }) 29 | 30 | test_that("types automatically coerced upwards", { 31 | expect_identical(vap_int(c(FALSE, TRUE), identity), c(0L, 1L)) 32 | 33 | expect_identical(vap_dbl(c(FALSE, TRUE), identity), c(0, 1)) 34 | expect_identical(vap_dbl(c(1L, 2L), identity), c(1, 2)) 35 | }) 36 | 37 | test_that("logical and integer NA become correct double NA", { 38 | expect_identical( 39 | vap_dbl(list(NA, NA_integer_), identity), 40 | c(NA_real_, NA_real_) 41 | ) 42 | }) 43 | 44 | test_that("map forces arguments in same way as base R", { 45 | f_map <- lap(1:2, function(i) function(x) x + i) 46 | f_base <- lapply(1:2, function(i) function(x) x + i) 47 | 48 | expect_equal(f_map[[1]](0), f_base[[1]](0)) 49 | expect_equal(f_map[[2]](0), f_base[[2]](0)) 50 | }) 51 | 52 | test_that("map works with calls and pairlists", { 53 | out <- lap(quote(f(x)), ~ quote(z)) 54 | expect_equal(out, list(quote(z), quote(z))) 55 | 56 | out <- lap(pairlist(1, 2), ~ .x + 1) 57 | expect_equal(out, list(2, 3)) 58 | }) 59 | 60 | 61 | 62 | context("imap") 63 | 64 | x <- setNames(1:3, 1:3) 65 | 66 | test_that("imap is special case of map2", { 67 | expect_identical(ilap(x, paste), Map(paste, x)) 68 | }) 69 | 70 | test_that("imap always returns a list", { 71 | expect_is(ilap(x, paste), "list") 72 | }) 73 | 74 | #test_that("atomic vector imap works", { 75 | #expect_true(all(imap_lgl(x, `==`))) 76 | #expect_length(imap_chr(x, paste), 3) 77 | #expect_equal(imap_int(x, ~ .x + as.integer(.y)), x * 2) 78 | #expect_equal(imap_dbl(x, ~ .x + as.numeric(.y)), x * 2) 79 | #expect_equal(imap_raw(as.raw(12), rawShift), rawShift(as.raw(12), 1) ) 80 | #}) 81 | 82 | #test_that("data frame imap works", { 83 | # expect_identical(imap_dfc(x, paste), imap_dfr(x, paste)) 84 | #}) 85 | 86 | -------------------------------------------------------------------------------- /tests/testthat/test-vap.R: -------------------------------------------------------------------------------- 1 | context("test-vap") 2 | 3 | test_that("vector apply functions", { 4 | ## generate data 5 | set.seed(12) 6 | d <- replicate(5, rnorm(10), simplify = FALSE) 7 | e <- replicate(5, sample(letters, 10), simplify = FALSE) 8 | m <- matrix(rnorm(25), 5) 9 | 10 | ##--------------------------------------------------------------------------## 11 | ## DBL ## 12 | ##--------------------------------------------------------------------------## 13 | 14 | ## standard 15 | expect_true(is.numeric(vap_dbl(e, ~ sum(nchar(.x))))) 16 | expect_true(is.numeric(vap_dbl(d, sum))) 17 | 18 | ## by row/column 19 | expect_true(is.numeric(vapr_dbl(m, ~ sum(nchar(.x))))) 20 | expect_true(is.numeric(vapr_dbl(m, sum))) 21 | expect_equal(length(vapr_dbl(m, sum)), nrow(m)) 22 | expect_true(is.numeric(vapc_dbl(m, ~ sum(nchar(.x))))) 23 | expect_true(is.numeric(vapc_dbl(m, sum))) 24 | expect_equal(length(vapc_dbl(m, sum)), ncol(m)) 25 | 26 | ##--------------------------------------------------------------------------## 27 | ## CHR ## 28 | ##--------------------------------------------------------------------------## 29 | 30 | ## standard 31 | expect_true(is.character(vap_chr(e, ~ paste(.x, collapse = "")))) 32 | expect_true(is.character(vap_chr(e, paste, collapse = ""))) 33 | 34 | ## by row/column 35 | expect_true(is.character(vapr_chr(m, ~ paste(.x, collapse = "")))) 36 | expect_true(is.character(vapc_chr(m, paste, collapse = ""))) 37 | expect_equal(length(vapc_chr(m, paste, collapse = "")), ncol(m)) 38 | 39 | ##--------------------------------------------------------------------------## 40 | ## LGL ## 41 | ##--------------------------------------------------------------------------## 42 | 43 | ## standard 44 | expect_true(is.logical(vap_lgl(d, ~ max(.x) > 3))) 45 | 46 | ## by row/column 47 | expect_true(is.logical(vapr_lgl(m, ~ max(.x) > 3))) 48 | expect_true(is.logical(vapc_lgl(m, ~ max(.x) > 3))) 49 | expect_equal(length(vapr_lgl(m, ~ max(.x) > 3)), nrow(m)) 50 | 51 | ##--------------------------------------------------------------------------## 52 | ## INT ## 53 | ##--------------------------------------------------------------------------## 54 | 55 | ## standard 56 | expect_true(is.integer(vap_int(d, length))) 57 | 58 | ## by row/column 59 | expect_true(is.integer(vapr_int(m, length))) 60 | expect_true(is.integer(vapc_int(m, length))) 61 | expect_equal(length(vapc_int(m, length)), ncol(m)) 62 | }) 63 | -------------------------------------------------------------------------------- /tools/readme/benchmark.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mkearney/dapr/744eb7e615d32fa97addc214b8c32528e36dfe36/tools/readme/benchmark.png --------------------------------------------------------------------------------