Разница между `paste`,` str_c`, `str_join`,` stri_join`, `stri_c`,` stri_paste`? - PullRequest
0 голосов
/ 02 ноября 2018

Каковы различия между всеми этими функциями, которые кажутся очень похожими?

1 Ответ

0 голосов
/ 02 ноября 2018
  • stri_join, stri_c и stri_paste происходят из пакета stringi и являются чистыми псевдонимами

  • str_c взято из stringr и является просто stringi::stri_join с параметром ignore_null, жестко заданным в TRUE, тогда как stringi::stri_join имеет значение по умолчанию FALSE , stringr::str_join является устаревшим псевдонимом для str_c

см

library(stringi)
identical(stri_join, stri_c)
# [1] TRUE
identical(stri_join, stri_paste)
# [1] TRUE

library(stringr)
str_c
# function (..., sep = "", collapse = NULL) 
# {
#   stri_c(..., sep = sep, collapse = collapse, ignore_null = TRUE)
# }
# <environment: namespace:stringr>

stri_join очень похож на base::paste с несколькими отличиями, перечисленными ниже:


1. sep = "" по умолчанию

По умолчанию он ведет себя как paste0, но paste0 потерял свой аргумент sep.

identical(paste0("a","b")        , stri_join("a","b"))
# [1] TRUE
identical(paste("a","b")         , stri_join("a","b",sep=" "))
# [1] TRUE
identical(paste("a","b", sep="-"), stri_join("a","b", sep="-"))
# [1] TRUE

str_c будет вести себя так же, как stri_join здесь.


2. Поведение с NA

Если вы вставите в NA с использованием stri_join, результат будет NA, а paste преобразует NA в "NA"

paste0(c("a","b"),c("c",NA))
# [1] "ac"  "bNA"
stri_join(c("a","b"),c("c",NA))
# [1] "ac" NA

str_c будет вести себя так же, как и stri_join здесь


3. Поведение с длиной 0 аргументов

При обнаружении значения длины 0 возвращается character(0), за исключением случаев, когда для ignore_null установлено значение FALSE, тогда это значение игнорируется. Он отличается от поведения paste, которое преобразует значение длины 0 в "" и, таким образом, содержит 2 последовательных разделителя на выходе.

stri_join("a",NULL, "b")  
# [1] character(0)
stri_join("a",character(0), "b")  
# [1] character(0)

paste0("a",NULL, "b")
# [1] "ab"
stri_join("a",NULL, "b", ignore_null = TRUE)
# [1] "ab"
str_c("a",NULL, "b")
# [1] "ab"

paste("a",NULL, "b") # produces double space!
# [1] "a  b" 
stri_join("a",NULL, "b", ignore_null = TRUE, sep = " ")
# [1] "a b"
str_c("a",NULL, "b", sep = " ")
# [1] "a b"

4. stri_join предупреждает больше

paste(c("a","b"),c("c","d","e"))
# [1] "a c" "b d" "a e"
paste("a","b", sep = c(" ","-"))
# [1] "a b"

stri_join(c("a","b"),c("c","d","e"), sep = " ")
# [1] "a c" "b d" "a e"
# Warning message:
#   In stri_join(c("a", "b"), c("c", "d", "e"), sep = " ") :
#   longer object length is not a multiple of shorter object length
stri_join("a","b", sep = c(" ","-"))
# [1] "a b"
# Warning message:
#   In stri_join("a", "b", sep = c(" ", "-")) :
#   argument `sep` should be one character string; taking the first one

5. stri_join быстрее

microbenchmark::microbenchmark(
  stringi = stri_join(rep("a",1000000),rep("b",1000),"c",sep=" "),
  base    = paste(rep("a",1000000),rep("b",1000),"c")
)

# Unit: milliseconds
#    expr       min       lq      mean    median       uq      max neval cld
# stringi  88.54199  93.4477  97.31161  95.17157  96.8879 131.9737   100  a 
# base    166.01024 169.7189 178.31065 171.30910 176.3055 215.5982   100   b
...