Sed ile satır sonu nasıl tespit edilir


15

Ben sadece son karakter newline, kullanarak değiştirme yürütmek için bir yol arıyorum sed.

Örneğin:

lettersAtEndOfLine

değiştirilir, ancak bu değiştirilmez:

lettersWithCharacterAfter&

Yeni sedsatırlarla iyi çalışmadığından, bu kadar basit değil

$ sed -E "s/[a-zA-Z]*\n/replace/" file.txt

Bu nasıl yapılabilir?

Yanıtlar:


21

Standart ile sed, bir dosyadan okunan metinde hiçbir zaman yeni satır görmezsiniz. Bunun nedeni sedsatır satır okur ve bu nedenle seddesen satırında geçerli satırın metninin sonunda yeni satır yoktur . Başka bir deyişle, sedyeni satırla sınırlandırılmış verileri okur ve sınırlayıcılar bir sedkomut dosyasının gördüklerinin bir parçası değildir .

Düzenli ifadeler olabilir demirlemiş kullanarak satırın sonunda $(veya başında kullanılarak ^). Bir ifadeyi satırın başına / sonuna sabitlemek, satırın herhangi bir yerinde değil, tam olarak orada eşleşmesini sağlar.

[A-Za-z]*Çizginin sonundaki desenle eşleşen herhangi bir şeyi bir şeyle değiştirmek istiyorsanız, deseni şu şekilde sabitleyin:

[A-Za-z]*$

... çizginin sonunda ve başka hiçbir yerde eşleşmeyecek.

Bununla birlikte, hiçbir şeyle[A-Za-z]*$ eşleşmediği için (örneğin, her satırın sonunda bulunan boş dize ), bir şeyin eşleşmesini zorlamanız gerekir , örn.

[A-Za-z][A-Za-z]*$

veya

[A-Za-z]\{1,\}$

Yani, sed komut satırınız böylece

$ sed 's/[A-Za-z]\{1,\}$/replace/' file.txt

-EBurada anahtarı kullanmadım çünkü gerekli değil. Bununla beraber, yazabilirdin

$ sed -E 's/[A-Za-z]+$/replace/' file.txt

Bu bir zevk meselesi.


Yorumlar uzun tartışmalar için değildir; bu görüşme sohbete taşındı .
Kusalananda

3
sed "s/[a-zA-Z]*$/replace/" input.txt > result.txt

Ya da, uzun karmaşık gereksiz yol:

Ben bu, hala sed kullanarak, tr yardımı ile yapılabilir öğrendim. Satırın sonunu temsil etmek için başka bir karakter atayabilirsiniz. Bu durumda "` "başka bir geçici karakter kullanılmalıdır. Satırın sonunu temsil etmek için "~" kullanalım:

tr '\n' '`' <input.txt >output.txt
sed -i "s/`/~`/" output.txt
tr '`' '\n' <output.txt >result.txt

Ve sonra gerçek arama ve değiştirme yapmak için "\ n" yerine "~" kullanın:

sed -i -E "s/[a-zA-Z]*~/replace/" result.txt

Ve sonra diğer satırlardaki ekstra karakteri temizleyin:

sed -i "s/~//" result.txt

Açıkçası, bunların hepsi bir araya getirilebilir ve sonuç olarak:

tr '\n' '`' <input.txt | sed -e "s/`/~`/" | tr '`' '\n' | sed -E -e "s/[a-zA-Z]*~/replace/" | sed "s/~//" > result.txt

3
Anladığımdan emin değilim ... Neden sadece çizginin sonuna demirlemiyorsun $? ör.s/[a-zA-Z]*$/replace/
don_crissti

1
2 puan: 1) İkincisi , dizenin sonunda sıfır harfe izin verdiği için \+yerine daha iyi kullanırsınız ; 2) Bir karakter sınıfı kullanabilirsiniz . Yani:*[[:alpha:]]sed 's/[[:alpha:]]\+$/replace/' file
glenn jackman

@glennjackman Artıdan önce ters eğik çizgi ne için? Bu toplama karakterine uymuyor mu?
Matthew D. Scholefield

1
Seçeneksiz GNU sed bu normal ifade sözdizimini-r kullanır .
glenn jackman

0

Gönderdiğiniz (kırık) kod snippet'inden, yeni satırı da değiştirmek istiyor gibi görünüyorsunuz. Bu durumda, regex sabitleme tek başına size yardımcı olamaz. Aşağıdaki bir çözümdür:

sed '/[[:alpha:]]\+$/{N;s/[[:alpha:]]\+\n/replace/}' your_file

Bozuldu:

  • /[a-zA-Z]\+$/{} regex ile eşleşen çizgilere, kıvrımların içine gelenleri uygulamak anlamına gelir.
  • Normal ifade, glenn jackman'ın yorumlarını dikkate almak için değiştirilmiş , kendi cevabınızda görüldüğü gibi ankraj kullanan kişidir .
  • Kıvrımların içinde N"bir sonraki satırı etkin arabelleğe ekle" ( sed"desen alanı" olarak adlandırılan)
  • Sonunda bu s///ifade sizin gerekli değişikliklerinizdir. Şimdi çalışıyor çünkü desen alanı iki ardışık satır içeriyor ve bu nedenle yeni satır bunun bir parçası.

0

Satırın sonunu bulmak için $ -sign öğesini kullanmanız yeterlidir :

Hat sonu bağlantısı olmadan:

sed -n '/pattern/p' file 

Hat sonu bağlantısı olmadan:

sed -n '/pattern$/p' file
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.