Mac OS X'te sed içindeki yeni satırlar


44

Bunun \nMac OS X altında sed'de çalışmadığını biliyorum.

# input
foo bar

Kullanırım,

echo "foo bar" | sed 's/ /\n/'

Ama sonuç aptalca, \nkaçamadı!

foonbar

Google’a danıştıktan sonra bir geçici çözüm buldum :

echo 'foo bar' | sed -e 's/ /\'$'\n/g'

Makaleyi okuduktan sonra ne \'$'\n/g'anlama geldiğini hala anlayamıyorum . Bazıları bunu bana açıklayabilir mi, yoksa yapmanın başka bir yolu var mı? Teşekkürler!


bu muhtemelen işe yarayacak:echo "foo bar" | tr ' ' '\n'
glenn jackman

3
Tavsiye için teşekkürler. Ama şu anda sadece yukarıdaki örneği bir örnek olarak kullanıyorum, nasıl kaçacağımı bilmem gerekiyor \n.
Ivan ZG Xiao,

Yanıtlar:


27

Şunları yapabilirsiniz brew install gnu-sedve çağrıları yerini sedile gsed.

Eğer "g" yi hazırlamak sedistemiyorsan, brew install gnu-sed --with-default-namesarayabilirsin sed.

(Düzenleme: demleme bayrağı güncellendi, şapka ucu Clément'e.)


Aynı yazılımı tüm platformlarda kullanmak (en sonunda benim için) Mac versiyonunun her bir özelliği ile uğraşmaktan çok daha kolaydır. Dikkat edin, seçenek şimdi --with-default-namesve değil --default-names . Bir koymak zorunda Ancak, bu seçenek, benim yüklemesinde çalıştı vermedi alias gsed=sedbenim de ~/.profilebunu yapmak için işe.
Clément

4
Bu çirkin bir geçici çözümdür. sedOS X'te neden böyle davrandığını ve yanlış olanın gnu-seddaha doğru olduğunu varsaydığını açıklamıyor . GNU bağımlısı olmayın ve uzun vadede sorunlardan kaçınmak için POSIX standartlarına uymayın.
octosquidopus

Apple, işletim sisteminin varsayılan olarak çalışmasını sağlamalıdır. Neden bir programın adını kullanıp daha sonra farklı bir şekilde çalışmasını sağlayın? Bundan dolayı bir saatimi boşa harcıyorum ...
rascio

@rascio - çünkü OS X BSD benzeri ve Linux Linux benzeridir.
idaresi

@rascio GNU sed'in yeni gelen olduğunu göreceksiniz. BSD sed 1979'a kadar uzanıyor ( en.wikipedia.org/wiki/Version_7_Unix ).
Duncan Bayne

24

Bunlar da işe yarar:

echo 'foo bar' | sed 's/ /\
/g'

echo 'foo bar' | sed $'s/ /\\\n/g'

lf=$'\n'; echo 'foo bar' | sed "s/ /\\$lf/g"

OS X'in sed'i \ndeğiştirme deseninde yorum yapmaz , ancak satır devam karakterinden önce gelen hazır bilgi satır beslemesini kullanabilirsiniz. Kabuk $'\n', sed komutu çalıştırılmadan önce değişmez bir satır besleme ile değiştirilir .


4
Neden sed $'s/ /\\\n/g'çalışıyor ama çalışmıyor sed $'s/\\\n/ /g'?
Alec Jacobson,

1
@alec Her yeni satırda sedayrıştırıldığında / ayrıldığından yeni satırları kaldırmak için linux / unix'te bile kullanamazsınız . Bunu linux / echo -e 'foo\nbar' | sed 's/\n//'
unix'te

10

Bulduğunuz geçici çözüm tek bir argüman dizgisine geçer sed -e.

Bu argüman, bilinen sed s/ / /gbiçiminde bir dize olarak son bulur .

Bu dize birbiri ardına iki kısım halinde oluşturulur.

İlk bölüm '...'formunda alıntı yapılır .

İkinci kısım $'...'formda alıntılanır .

's/ /\'Bölüm sıyrılıp tek tırnak alır, ancak aksi takdirde komut satırında arar gibi sed geçer. Yani, ters eğik çizgi bash tarafından yenilmez, sed'e geçer.

$'\n/g'Bölüm dolar işareti ve sıyrılıp tek tırnak alır ve \nbir satır karakteri dönüştürülmüş olur.

Hep birlikte, argüman olur

s / / \ newline/ g

[Bu eğlenceliydi. Bunu çözmek biraz zaman aldı. İlginç bir soru için +1.]


7

İfade $'...', genişletilmiş standart kaçış dizileri ile üretilen bir bash-izmdir .... Bundan \'önce sadece alıntı yapılan bölümün sonuna kadar bir ters eğik çizgi anlamına gelir, sonuçta elde edilen dizgedir s/ /\. (Evet, bir dizgenin ortasındaki alıntıyı değiştirebilirsiniz; dizginin sonuna gelmez.)

POSIX standardı sedyalnızca \narama modelinin bir parçası olarak kabul eder . OS X sed, kesinlikle POSIX uyumlu olan FreeBSD'yi kullanıyor ; GNU, her zamanki gibi, daha sonra ekstra malzeme ve Linux kullanıcıları tüm düşünüyorum ekleyen bu "standart" bir çeşit (ikisinden birinin bir standartlar işlemek olsaydı belki daha etkiledi olurdu).


Şimdi $'...'kısmı anlıyorum . Ama ... nedir s/ /\ ? Ne demek istiyorsun switch quoting?
Ivan ZG Xiao,

2
'...'bir çeşit kabuk alıntıdır; $'...'başka bir şey. Orada da "..."ve \xtek bir karakter alıntı. Bunları tek bir kelimeyle birleştirebilirsiniz, burada ne yapıldığı, normal ''bir $''dizgeden dize çevirmek için \n. Gerisi gelince, o bir sedkomut ( s/text/replacement/flags) inşa ediyor . Bu durumda, komutun sonunda eklenmiş olan değişmez çizgiyi korumak için bir ters eğik çizgi de dahil olmak üzere başlatılır $'\n/g'. Sonuç, tüm ( /gbayrak) boşluklarını yeni satırlarla değiştirmektir.
geekosaur

1

Ne olduğunu görsel olarak görmek çok kolay. Sadece dize yankı!

echo 's/$/\'$'\n/g'

sonuçlanır

s/$/\
/g

hangi eşdeğer s/$/\newline/g

Eğer daha \önce fazladan sahip değilseniz newline, kabuk newline, komutun erken bitimi olarak yorumlanırdı .

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.