Bir for döngüsü kullanarak bir proje dizinindeki tüm başlık dosyalarına ve kaynak dosyalarına lisans başlığı eklemeye çalışıyorum. Bu işe yaramıyor, kullanan başka bir yaklaşım var sed
mı?
Bir for döngüsü kullanarak bir proje dizinindeki tüm başlık dosyalarına ve kaynak dosyalarına lisans başlığı eklemeye çalışıyorum. Bu işe yaramıyor, kullanan başka bir yaklaşım var sed
mı?
Yanıtlar:
for f in **/*.cpp; do
cat header_file $f > $f.new
mv $f.new $f
done
globstar
çalışması için bash'ta açmanız gerektiği belirtilmelidir .
Bu, Daniel Serodio'nun cevabı hakkında az çok geniş bir yorum . Bir yorum olarak yazmaya başladım, ama çok hızlı büyüdü ...
Bir bash globunun özyinelemesi için gerektirir shopt -s globstar
. Globstar'ı etkinleştirmelisiniz, aksi takdirde **
çalışmaz. Globstar kabuk seçeneği, bash'ın 4. sürümüne tanıtıldı.
Gibi bir dizini işlemekten kaçınmak my.cpp/
için testi kullanın [[ -f $f ]]
... Test çift köşeli parantez içindeyse, değişkenlerin çift tırnak içine alınması gerekmez.
Kullanarak eşleşen shopt -s nullglob
dosya bulunma olasılığını da düşünebilirsiniz, bu da hiçbir dosyayla eşleşen desenlerin kendilerinden ziyade boş bir dizeye genişlemesine izin verir.
Çok sayıda kalıbı işlemek için, topak desen zincir olabilir: **/*.cpp **/*.h
fakat kabuk seçeneği zaman, belki de tercihan, extglob olan ilgili yoluyla shopt -s extglob
, aşağıdakiler gibi bu tür yapıları kullanabilir **/*.@(cpp|h)
dosya sistemi üzerinden birden fazla geçiş kaçınan; her desen için bir kez.
Eklenmek istiyorsanız .files
, .*.cpp
vb. Kullanın veya kullanınshopt -s dotglob
Borulmakta olan bir dosyayı güvenli bir şekilde değiştirmek için sponge
paketten kullanın moreutils
(size kendi geçici dosyanızı oluşturma ihtiyacını azaltır)
printf "// The License\n\n" > /tmp/$USER-license
shopt -s globstar nullglob extglob
for f in **/*.@(cpp|h) ;do
[[ -f $f ]] && cat "/tmp/$USER-license" "$f" | sponge "$f"
done
[[
boş bir değeri zarifçe işleyebilir $f
.
unset x; [ -f $x ] && echo exists
"var" raporları ... (sabit)
**/*.@(cpp|h)
ile$( find . -name "*.h" -name "*.cpp")
Teşekkürler @fred, @maxmackie, @enzotib.
Lütfen takip ettiğim prosedürü kontrol edebilir misiniz?
#!/bin/sh
# script to copy the headers to all the source files and header files
for f in *.cpp; do
if (grep Copyright $f);then
echo "No need to copy the License Header to $f"
else
cat license.txt $f > $f.new
mv $f.new $f
echo "License Header copied to $f"
fi
done
aksi takdirde lisans başlığı birden çok defa kopyalanır.
Lütfen proje dizini ve alt dizinlerindeki tüm üstbilgileri ve kaynakları incelemek için bir model önerin.
@Fred'nin ne önerdiğini tam olarak anlayamadım.
targln=2; findln=$(sed -rne $targln'{\|// Copyright|=;q}' "$f"); if ((findln==targln));then
... ama elbette, her şeyin üstünde ve ötesinde, önce iyice test edin ... PS. O burada ders için eşit olduğunu Unix ve Linux bu tür post ekstralar , orijinal söz konusu değil ... bir cevap olarak
grep
, -q
seçeneğine ekleyin grep
. Etrafınıza her zaman çift tırnak ekleyin $f
.
Bunu ile ex
ya ed
da tercih ederseniz yapabilirsiniz (bunu istediğiniz gibi yapmamalısınız sed
, sed
akışları düzenlemek için tasarlanmıştır, -i
çeşitli nedenlerden dolayı kötü bir fikirdir):
shopt -s globstar
for _file in **/*.@(cpp|h); do
ed -s "${_file}" << EOF
0a
/* This file is licensed under the foo license.
All copyright strictly enforced by the copyright monster. */
.
w
EOF
done
sed -i
kötü bir fikir?
sed -i
ve sabit bağlantıları keserek beklenmeyen davranışlara neden olur. En iyi ihtimalle sezgisel değildir, daha da kötüsü aktif olarak zararlıdır.
#!/bin/bash
for i in `find . -name '*.[m|h]'` # or whatever other pattern...
do
echo $i
if ! grep -q Copyright $i
then
cat copyright.txt $i >$i.new && mv $i.new $i
fi
done
enter code here
Gerhard Gappmeier'in blogu - Kaynak dosyaların dosya başlıklarını tekrar tekrar nasıl değiştirilir?
Blog yayını, tar.gz
gerekli dosyaları içeren bir dosya ekledi.
header.template
Özel bir yorum yazabileceğiniz bir dosyaya sahiptir, birden fazla satıra yayılabilir.
remove_header.awk
Varolan üstbilgileri yeni üstbilgiyle değiştiren bir komut dosyası vardır.
Çalıştırmak için:
find . -name "*.h" -exec ~/rh/replace_header.sh {} \;