Câu trả lời:
Thêm vào gia đình của các giải pháp :-).
duplicator.sh
:
for i; do echo -n "$i $i "; done; echo
Thực hiện và bây giờ:
$ ./duplicator.sh dog cat bird whale
dog dog cat cat bird bird whale whale
Ngoài ra, dưới dạng hàm shell, ví dụ: có thể sử dụng lại trong tập lệnh:
duplicator() {
for i; do echo -n "$i $i "; done; echo
}
mà sau đó có thể được chạy trực tiếp ở nơi được định nghĩa là
duplicator dog cat bird whale
Bạn có thể sử dụng sed
:
sed -r 's/(\S+)/\1 \1/g' filename
Nếu bạn muốn lưu các thay đổi vào tệp tại chỗ, hãy nói:
sed -i -r 's/(\S+)/\1 \1/g' filename
Bạn cũng có thể sử dụng perl
:
perl -M5.10.0 -ne 'say join " ", map{$_, $_} split " ";' filename
(Thêm -i
tùy chọn để lưu các thay đổi vào tệp tại chỗ.)
Hoặc, theo đề xuất của terdon :
perl -M5.10.0 -ane 'say join " ", map{$_, $_} @F;' filename
Trích dẫn từ perlvar
:
@F
Mảng
@F
chứa các trường của mỗi dòng được đọc khi chế độ tự động bật được bật. Xem perlrun cho-a
chuyển đổi. Mảng này là đặc thù của gói và phải được khai báo hoặc đặt tên gói đầy đủ nếu không có trong gói chính khi chạy bên dướistrict 'vars'
.
sed -r 's/\S+/& &/g'
.
-a
:perl -M5.10.0 -ane 'say join " ", map{$_, $_} @F;'
Điều này sẽ là gì nếu không có awk/gawk
câu trả lời:
$ 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
Nếu một dòng mới chấm dứt là quan trọng:
$ awk '{ for(i=1;i<=NF+1;i+=1/2) { printf("%s ",$i); }} END{print ""}' <<<"dog cat bird whale"
for(i=1;i<=NF;++i) printf "%s %s ",$i,$i;
cả ngắn hơn và dễ đọc hơn, IMHO.
s="dog cat bird wale"
ss=$( tr ' ' '\n' <<< "$s" | sed p | tr '\n' ' ' )
echo "$ss"
dog dog cat cat bird bird wale wale
sed -n 'p;p'
- tôi nghĩ điều đó minh bạch hơn về những gì nó đang làm.
Nếu bạn có chuỗi của bạn trong một biến, giả sử foo="dog cat bird whale"
, bạn có thể làm:
Bash tinh khiết:
$ echo "$foo" | (read a b c d && echo "$a $a $b $b $c $c $d $d")
dog dog cat cat bird bird whale whale
Giải thích: Các dấu ngoặc đơn là cần thiết để read
và echo
xảy ra trong cùng một mạng con và do đó có thể chia sẻ các biến. Nếu không có họ, họ echo
sẽ chỉ in một dòng trống.
lõi:
$ 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
Giải thích: Các -o
lá cờ của join
cho phép bạn thiết lập các định dạng đầu ra. Ở đây, tôi đang bảo nó in trường thứ nhất của tệp 1 ( 1.1
), tiếp theo là trường thứ 2 của tệp thứ 1 ( 1.2
), v.v ... Bằng cách đó, mỗi trường của tệp thứ 1 được in hai lần. Tuy nhiên, join
được thiết kế để, tốt, tham gia hai dòng đầu vào trên một trường chung. Vì vậy, tôi cũng chuyển cho nó một dòng trống ( <(echo)
) và sau đó bỏ qua nó. Trường -j
đặt trường tham gia, đặt trường này thành trường không tồn tại (lần thứ 5) join
để in toàn bộ dòng.
Nếu bạn không quan tâm đến khoảng trắng hoặc thứ tự đầu vào, bạn có thể làm
$ paste <(echo $foo) <(echo $foo)
dog cat bird wale dog cat bird wale
Perl 1:
$ echo $foo | perl -lane 'push @k, $_,$_ for @F; print "@k"'
dog dog cat cat bird bird whale whale
Giải trình:
-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.
Kịch bản trên sẽ lưu mỗi trường (từ @F
) hai lần trong mảng @k
và sau đó in @k
. Nếu bạn không cần dòng mới, bạn có thể đơn giản hóa
$ echo $foo | perl -ane 'print " $_ $_" for @F'
Perl 2:
$ echo $foo | perl -0040 -pne 'print "$_"' | paste - -
dog dog cat cat bird bird whale whale
Giải thích: Các -0
tùy chọn thiết lập tách hồ sơ đầu vào (như là một hệ thập lục phân hoặc số bát phân, xem ở đây cho các chuyển đổi). Ở đây, tôi đang đặt nó thành bát phân 040
là một không gian. Việc in -p
giúp perl
mỗi "dòng" đầu vào và vì chúng ta đã đặt dấu tách bản ghi thành khoảng trắng, các dòng hiện được xác định bởi khoảng trắng, vì vậy mỗi trường được in hai lần.
awk
:
$ echo $foo | awk '{for(i=1;i<=NF;i++){$i=$i" "$i;} 1;}'
dog dog cat cat bird bird whale whale
Giải thích: NF
là số lượng các trường, do đó, tập lệnh ở trên đi qua từng trường và nối nó với chính nó. Khi đã xong, chúng tôi in dòng ( 1;
chỉ là tốc ký để in).
Bây giờ cho một python
câu trả lời:
Từ dòng lệnh:
$ python -c "import sys; s=sys.argv[1:]; print(' '.join(j for i in zip(s,s)for j in i));" dog cat bird whale
Từ stdin:
$ python -c "s=input().split(); print(' '.join(j for i in zip(s,s)for j in i));" <<<"dog cat bird whale"
Kết quả trong cả hai trường hợp:
dog dog cat cat bird bird whale whale
Hơi quá đầu, nhưng một haskell
câu trả lời:
$ ghc -e "getLine >>= putStrLn . unwords . (concatMap $ replicate 2) . words" <<<"dog cat bird whale"
dog dog cat cat bird bird whale whale
Một cách tiếp cận khác, cũng chỉ sử dụng các nội dung bash
$ string="dog cat bird whale"
$ twix() { while [[ ! -z $1 ]]; do printf "%s %s " $1 $1; shift; done; }
$ twix $string
dog dog cat cat bird bird whale whale
Tôi không thấy bất kỳ lợi ích nào so với câu trả lời hàng đầu, chỉ để thể hiện một cách hơi khác, có thể phù hợp hơn cho một số mục đích.
echo
cũng là một shell dựng sẵn trong Bash (thử nghiệm type echo
).