Birden fazla boşluk tek bir sekmeyle nasıl değiştirilir


27

Çeşitli boşluklarla ayrılmış bazı sütunlar içeren bazı metin dosyalarım var, ancak bunun yerine ayırıcı olarak tek bir sekmeye ihtiyacım var. Bash'de yapmak mümkün mü?


Harika girdi için teşekkürler, ancak bir sütun içinde bazı tek boşluklar var, bu yüzden tek bir boşluk bırakmaktan kaçınmalıyım. Bunun için üzgünüm, bilgiler.
user_unknown

Yanıtlar:


31

Dizileri dönüştürmek için birden fazla alana bir sekmeye ama yalnız bireysel boşluk bırakın :

sed 's/ \+ /\t/g' inputfile > outputfile

Bunu birkaç dosya için yapmak için:

for inputfile in *
do
    sed 's/ \+ /\t/g' "$inputfile" > tmpfile && mv tmpfile "$inputfile"
done

veya

for inputfile in *
do
    sed -i.bak 's/ \+ /\t/g' "$inputfile"
done

veya

find . -type f -exec sed -i.bak 's/ \+ /\t/g' {} \;

sed: -e expression #1, char 1: unknown command: `.'
Aaron Franke

@AaronFranke: Hangi komutu denediniz? Cevabımdaki hiçbir örnek bu hatayı üretmemeli.
sonraki duyuruya kadar duraklatıldı.

Üzgünüm, açıklığa kavuşturmalıydım. findAltta biri.
Aaron Franke

@AaronFranke: GNU sed, yedekleme uzantısından önce bir boşluk bırakmak istemiyor. Cevabımı düzenledim. Rapor için teşekkürler.
sonraki duyuruya kadar duraklatıldı.

7

Karakteriniz birden fazla sekme ise şunları da kullanabilirsiniz tr -s:

-s, --squeeze-repeats   replace each input sequence of a repeated character
                        that is listed in SET1 with a single occurrence

Örneğin:

my_file.txt | tr -s " "

Tüm beyaz alanlar bir olacak.


OP'nin istediği şey bu değil.
RonJohn,

5

Birkaç sedboşluğu sekmeyle değiştirmek için kullanabilirsiniz :

Bir veya daha fazla boşluğu bir sekmeyle değiştirmek için örnek:

cat spaced-file | sed 's/ \+/\t/g' > tabbed-file

OP, uzay sayısının değişken olduğunu söyledi , bu yüzden bu çözümün işe yarayacağını sanmıyorum.
Mikel

@Mikel. Hata. Gösterdiğin için teşekkürler. Değişken boşluklarla eşleşmeye izin vermek için yazıyı düzenledim.
IvanGoneKrazy

Buradaki en yararlı cevap.
Luís de Sousa,

3

Sadece kullanarak en kolay cevap bash:

while read -r col1 col2 col3 ...; do
    echo -e "$col1\t$col2\t$col3..."
done <file

Sütunların bir değişken vardır varsa, bunu yapabilirsiniz, ancak yalnızca çalışacak bash, değil sh:

while read -r -a cols; do
    (
        IFS=$'\t'
        echo "${cols[*]}"
    )
done <file

Örneğin

while read -r -a cols; do
    (
        IFS=$'\t'
        echo "${cols[*]}"
    )
done <<EOF
a b   c
d   e    f
  g h i
EOF

üretir:

a   b   c
d   e   f
g   h   i

(aralarında bir sekme var, ancak buraya yapıştırdığımda görmek zor)

Ayrıca kullanarak yapabileceğini sedya trama ihbar başlangıcında boşlukları elleçleme farklı sonuçlar üretir.

sed:

$ sed 's/  */\t/g' << EOF
a b   c
d   e    f
  g h i
EOF
a       b       c
d       e       f
        g       h       i

tr:

$ tr -s ' ' '\t' <<EOF
a b   c
d   e    f
  g h i
EOF
a       b       c
d       e       f
        g       h       i


2

Aşağıdaki SED betiğini deneyin:

 sed 's/  */<TAB>/g' <spaces-file > tabs-file

<TAB> TAB tuşuna basıldığında.


0

Bu çok basit bir çözüm:

    sed -E 's/\s+/\t/g' your_file > new_file

sed temelde bu şekilde çalışır (sed 's / old_pattern / new_pattern / g'). Bu durumda, eski kalıp "\ s +" dır, bu da "s" alanını bir veya daha fazla zaman "+" ve ters eğik çizgiyi "\" bulmak anlamına gelir.
Yeni desen, düzenli ifade biçiminde yazılan "\ t" sekmesidir ve "g", "global" olarak tüm satırlara uygulanır.


1
Merhaba ve süper kullanıcıya hoş geldiniz. Çözümünüzü açıklamak için zaman ayırmalısınız. * Nix sistemlerine aşina olmayan biri için, sed ve düzenli ifadeler, bu garip karakter yığını gibi görünüyor.
Mogget
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.