2011-08-26 24 views
277

¿Cómo puedo fusionar/combinar dos valores en R? Por ejemplo tengo:¿Cómo se pueden concatenar 2 cadenas?

tmp = cbind("GAD", "AB") 
tmp 
#  [,1] [,2] 
# [1,] "GAD" "AB" 

Mi objetivo es conseguir tmp como una cadena

tmp_new = "GAD,AB" 

¿Qué función puede hacer esto por mí?

+0

La mayoría de las respuestas aquí se rompen si las cadenas son vectores, como las notas de respuesta de @ RichardScriven. – smci

+0

@smci ¿Qué hay de la pequeña respuesta que he publicado? ¿Alguna sugerencia para mejorarlo? –

Respuesta

13

Dada la matriz, tmp, que creó:

paste(tmp[1,], collapse = ",") 

Asumo hay alguna razón por la cual está creando una matriz usando cbind, en lugar de simplemente:

tmp <- "GAD,AB" 
357
paste() 

es el camino a seguir. Como señalaron los carteles anteriores, pegar puede hacer dos cosas:

concatenar los valores en una "cadena", p. Ej.

> paste("Hello", "world", sep=" ") 
[1] "Hello world" 

donde el argumento sep especifica el carácter (s) para ser utilizado entre los argumentos para concatenar, o contraer vectores de caracteres

> x <- c("Hello", "World") 
> x 
[1] "Hello" "World" 
> paste(x, collapse="--") 
[1] "Hello--World" 

donde el argumento collapse especifica el carácter (s) para ser utilizado entre los elementos del vector que se colapsará.

Usted puede incluso combinar ambas cosas:

> paste(x, "and some more", sep="|-|", collapse="--") 
[1] "Hello|-|and some more--World|-|and some more" 

Espero que esto ayude.

+6

Mezclar cadenas y vectores o vectores de diferentes longitudes es un poco demasiado flexible en 'paste()' para mi gusto. Por ejemplo, 'paste (c ('a', 'b'), 'blah', c (1,2,3))' da como resultado '" a blah 1 "" b blah 2 "" a blah 3 "' . Básicamente, crea un vector de cadenas de la misma longitud que el vector más largo que se pasa, y coloca los otros vectores/cadenas en la misma longitud. Mucho espacio para el comportamiento accidental allí. – naught101

+1

Cierto, pero ¿puede proporcionar un enfoque alternativo que aborde la pregunta? – Rainer

+1

no - su respuesta es correcta (como lo son la mayoría de las otras respuestas que dicen lo mismo). Solo estaba notando que el comportamiento del pegado es inusual en su flexibilidad. – naught101

70

help.search() es una función útil, p.

> help.search("concatenate") 

lo llevará a paste().

20

Como han señalado otros, paste() es el camino a seguir. Pero puede ser molesto tener que escribir paste(str1, str2, str3, sep='') cada vez que desee el separador no predeterminado.

Puede crear fácilmente funciones de envoltura que lo hacen mucho más simple.Por ejemplo, si usted se encuentra concatenación de cadenas sin separador muy a menudo, puede hacer:

p <- function(..., sep='') { 
    paste(..., sep=sep, collapse=sep) 
} 

o si a menudo desea unirse a las cadenas de un vector (como implode() de php):

implode <- function(..., sep='') { 
    paste(..., collapse=sep) 
} 

Permite que hagas hacer esto:

p('a', 'b', 'c') 
#[1] "abc" 
vec <- c('a', 'b', 'c') 
implode(vec) 
#[1] "abc" 
implode(vec, sep=', ') 
#[1] "a, b, c" 

Además, no es el construido en paste0, que hace lo mismo que mi implode, pero sin allo ala separadores personalizados. Es ligeramente más eficiente que paste().

32

Para la primera respuesta no paste(), podemos mirar stringr::str_c() (y luego toString() a continuación). No ha existido tanto tiempo como esta pregunta, por lo que creo que es útil mencionar que también existe.

Muy fácil de usar, como puede ver.

tmp <- cbind("GAD", "AB") 
library(stringr) 
str_c(tmp, collapse = ",") 
# [1] "GAD,AB" 

De la descripción del archivo de documentación, encaja perfectamente con este problema.

Para comprender cómo str_c funciona, debe imaginar que está creando una matriz de cadenas. Cada argumento de entrada forma una columna y se expande a la longitud del argumento más largo, utilizando las reglas de reciclaje habituales. La cadena sep se inserta entre cada columna. Si el colapso es NULL, cada fila se contrae en una sola cadena. Si no es nula esa cadena se inserta al final de cada fila, y toda la matriz se colapsó en una sola cadena.

Agregado 13/04/2016: No es exactamente la misma que su salida deseada (espacio adicional), pero nadie lo ha mencionado tampoco. toString() es básicamente una versión de paste() con collapse = ", " no modificable, por lo que puede hacer

toString(tmp) 
# [1] "GAD, AB" 
+3

Heh, esta es la única respuesta que aborda el hecho de que tmp es un vector, y no solo un conjunto de valores - 'paste' no hace vectores . La otra opción es 'do.call (pegar, como.lista (tmp))'. – naught101

22

Alternativamente, si su objetivo es dar salida directamente a un archivo o la salida estándar, puede utilizar cat:

cat(s1, s2, sep=", ") 
+4

Entonces, ¿qué sentido tiene publicar una respuesta 'paste '4 años después, cuando ya hay alrededor de una docena de respuestas' paste'? –

+3

En ese momento, me resultó útil resumir varias respuestas por mi cuenta. El objetivo no era recoger votos, sino ayudar a otros a filtrar a través de las muchas soluciones ofrecidas. A menudo eso es lo que estoy buscando. – Megatron

16

usted puede crear propio operador:

'%&%' <- function(x, y)paste0(x,y) 
"new" %&% "operator" 
[1] newoperator` 

también puede redefinir 'y' (&) op rador:

'&' <- function(x, y)paste0(x,y) 
"dirty" & "trick" 
"dirtytrick" 

jugar con la sintaxis de línea de base es feo, pero también lo está utilizando paste()/paste0() si se trabaja sólo con su propio código se puede (casi siempre) reemplazar lógica & and operador con * y hacer la multiplicación de los valores lógicos en lugar de utilizar lógica 'y &'

+0

@Richard Scriven mayby ​​No entiendo, pero parece sencillo, comparar: 'paste0 (como matriz (iris [1: 4]), as.matriz (iris [1: 4]))' y 'como. matrix (iris [1: 4])% &% as.matrix (iris [1: 4]) ' – Qbik

11

Otra forma:

sprintf("%s you can add other static strings here %s",string1,string2) 

a veces útil que paste() función. %s denota el lugar donde se incluirán las cadenas subjetivas.

Tenga en cuenta que este será muy útil a medida que tratan de construir un camino:

sprintf("/%s", paste("this", "is", "a", "path", sep="/")) 

salida

/this/is/a/path 
+0

para C programadores que trabajan con R, sprintf es familiar y útil para" concatenar dos cuerdas " – subsci

+0

Mucho mejor. 'paste' no es lo suficientemente flexible si desea agregar algo a una cadena. – displayname

1

Considérese el caso en que las cadenas son las columnas y el resultado debe ser una nueva columna :

df <- data.frame(a = letters[1:5], b = LETTERS[1:5], c = 1:5) 

df$new_col <- do.call(paste, c(df[c("a", "b")], sep = ", ")) 
df 
# a b c new_col 
#1 a A 1 a, A 
#2 b B 2 b, B 
#3 c C 3 c, C 
#4 d D 4 d, D 
#5 e E 5 e, E 

Opcionalmente, omita la [c("a", "b")] subconjuntos si todo colum ns necesita ser pegado.

# you can also try str_c from stringr package as mentioned by other users too! 
do.call(str_c, c(df[c("a", "b")], sep = ", ")) 
+0

Ok, pero las bibliotecas 'stringi, stringr' son más rápidas. – smci

Cuestiones relacionadas