Tengo una cadena como:dog cat bird whale
y quiero conseguirdog dog cat cat bird bird whale whale
Todas las palabras están en la misma línea. ¿Alguna idea?
Respuesta1
Sumando a la familia de soluciones :-) .
duplicator.sh
:
for i; do echo -n "$i $i "; done; echo
Haz ejecutable, y ahora:
$ ./duplicator.sh dog cat bird whale
dog dog cat cat bird bird whale whale
Alternativamente como función de shell, por ejemplo, para ser reutilizable dentro de un script:
duplicator() {
for i; do echo -n "$i $i "; done; echo
}
que luego se puede ejecutar directamente donde se define como
duplicator dog cat bird whale
Respuesta2
Podrías usar sed
:
sed -r 's/(\S+)/\1 \1/g' filename
Si desea guardar los cambios en el archivo in situ, diga:
sed -i -r 's/(\S+)/\1 \1/g' filename
También podrías usar perl
:
perl -M5.10.0 -ne 'say join " ", map{$_, $_} split " ";' filename
(Agregue la -i
opción para guardar los cambios en el archivo in situ).
O, como sugiereterdón:
perl -M5.10.0 -ane 'say join " ", map{$_, $_} @F;' filename
Citando deperlvar
:
@F
La matriz
@F
contiene los campos de cada línea leída cuando el modo de división automática está activado. Consulte perlrun para el-a
conmutador. Esta matriz es específica del paquete y debe declararse o recibir un nombre de paquete completo si no está en el paquete principal cuando se ejecuta bajostrict 'vars'
.
Respuesta3
¿Qué sería esto sin una awk/gawk
respuesta?
$ awk '{ for(i=1;i<=NF+1;i+=1/2) { printf("%s ",$i); }}' <<<"dog cat bird whale"
dog dog cat cat bird bird whale whale
Si una nueva línea final es importante:
$ awk '{ for(i=1;i<=NF+1;i+=1/2) { printf("%s ",$i); }} END{print ""}' <<<"dog cat bird whale"
Respuesta4
Si tiene su cadena en una variable, digamos foo="dog cat bird whale"
, podría hacer:
Fiesta pura:
$ echo "$foo" | (read a b c d && echo "$a $a $b $b $c $c $d $d") dog dog cat cat bird bird whale whale
Explicación:Los paréntesis son necesarios para que
read
yecho
ocurran en el mismo subnivel y, por lo tanto, puedan compartir variables. Sin ellos,echo
simplemente imprimirían una línea en blanco.coreutils:
$ join -j 5 -o 1.1,1.1,1.2,1.2,1.3,1.3,1.4,1.4 <(echo $foo) <(echo) dog dog cat cat bird bird whale whale
Explicación:La
-o
bandera dejoin
le permite configurar el formato de salida. Aquí, le digo que imprima el primer campo del primer archivo (1.1
), seguido del segundo campo del primer archivo (1.2
), etc. De esa manera, cada campo del primer archivo se imprime dos veces. Sin embargo,join
está diseñado para, bueno, unirsedoslíneas de entrada en un campo común. Entonces, también le paso una línea en blanco (<(echo)
) y luego la ignoro. Establece-j
el campo de unión, estableciéndolo en uno que no existe (el quinto) hacejoin
que se imprima la línea completa.Si no le importan los espacios en blanco o el orden de entrada, puede hacerlo
$ paste <(echo $foo) <(echo $foo) dog cat bird wale dog cat bird wale
Perla 1:
$ echo $foo | perl -lane 'push @k, $_,$_ for @F; print "@k"' dog dog cat cat bird bird whale whale
Explicación:
-l: adds a newline to each print call (among other things) -a: turns on field splitting, fields are saved as @F -n: process input line by line -e: give a script as a command line parameter.
El script anterior guardará cada campo (de
@F
) dos veces en la matriz@k
y luego imprimirá@k
. Si no necesita la nueva línea final, puede simplificarla a$ echo $foo | perl -ane 'print " $_ $_" for @F'
Perla 2:
$ echo $foo | perl -0040 -pne 'print "$_"' | paste - - dog dog cat cat bird bird whale whale
Explicación:La
-0
opción establece el separador de registros de entrada (como un número hexadecimal u octal, consulteaquípara conversiones). Aquí lo estoy configurando en octal,040
que es un espacio. Hacen-p
imprimirperl
cada "línea" de entrada y como hemos configurado el separador de registros en espacio, las líneas ahora están definidas por espacios, por lo que cada campo se imprime dos veces.awk
:$ echo $foo | awk '{for(i=1;i<=NF;i++){$i=$i" "$i;} 1;}' dog dog cat cat bird bird whale whale
Explicación:
NF
es el número de campos, por lo que el script anterior revisa cada campo y lo agrega a sí mismo. Una vez hecho esto, imprimimos la línea (1;
es solo una abreviatura de imprimir).