Jika saya menjalankan perintah ini dari skrip:
#my.sh
PWD=bla
sed 's/xxx/'$PWD'/'
...
$ ./my.sh
xxx
bla
itu baik-baik saja.
Tapi, jika saya jalankan:
#my.sh
sed 's/xxx/'$PWD'/'
...
$ ./my.sh
$ sed: -e expression #1, char 8: Unknown option to `s'
Saya membaca dalam tutorial bahwa untuk mengganti variabel lingkungan dari shell Anda harus berhenti, dan 'mengutip' $varname
bagian sehingga tidak diganti secara langsung, yang saya lakukan, dan yang berfungsi hanya jika variabel didefinisikan segera sebelumnya.
Bagaimana saya bisa mendapatkan sed untuk mengenali $var
variabel lingkungan seperti yang didefinisikan dalam shell?
set -x
di shell untuk mendapatkan shell untuk mengulangi setiap perintah sebelum dieksekusi. Ini dapat menghilangkan banyak kebingungan. (Juga, saya sering menggunakanset -u
untuk membuat de-referensi variabel yang tidak disetel kesalahan yang sulit. (Lihatset -e
juga.))Jawaban:
Dua contoh Anda terlihat identik, yang membuat masalah sulit didiagnosis. Masalah potensial:
Anda mungkin perlu tanda kutip ganda, seperti pada
sed 's/xxx/'"$PWD"'/'
$PWD
mungkin mengandung garis miring, dalam hal ini Anda perlu menemukan karakter yang tidak terkandung$PWD
untuk digunakan sebagai pembatas.Untuk mengatasi kedua masalah sekaligus, mungkin
sumber
Selain jawaban Norman Ramsey, saya ingin menambahkan bahwa Anda dapat mengutip dua kali seluruh string (yang dapat membuat pernyataan lebih mudah dibaca dan lebih sedikit kesalahan cenderung).
Jadi jika Anda ingin mencari 'foo' dan menggantinya dengan konten $ BAR, Anda dapat menyertakan perintah sed dalam tanda kutip ganda.
Dalam yang pertama, $ BAR tidak akan berkembang dengan benar sedangkan di $ BAR kedua akan berkembang dengan benar.
sumber
"2,$s/^/$foo/"
yang$s
akan ditafsirkan sebagai variabel juga dan seharusnya tidak.Anda dapat menggunakan karakter lain selain "/" sebagai pengganti:
sumber
sed
muntah karena menafsirkan/
dalam isi $ 2. Inilah tepatnya yang saya butuhkan untuk melewatinya. Terima kasih atas tip yang bagus!Alternatif mudah lainnya:
Karena
$PWD
biasanya akan berisi garis miring/
, gunakan|
sebagai ganti/
untuk pernyataan sed:sumber
$PWD
...?Dengan edit pertanyaan Anda, saya melihat masalah Anda. Katakanlah direktori saat ini adalah
/home/yourname
... dalam hal ini, perintah Anda di bawah ini:akan diperluas ke
yang tidak valid Anda harus meletakkan
\
karakter di depan masing-masing/
dalam $ PWD Anda jika Anda ingin melakukan ini.sumber
cara buruk: ubah pembatas
mungkin itu bukan jawaban terakhir,
Anda tidak dapat mengetahui karakter apa yang akan muncul
$PWD
,/
:
ATAU@
.cara yang baik adalah mengganti karakter spesial di
$PWD
.cara yang baik: melarikan diri pembatas
misalnya: coba ganti
URL
sebagai $ url (ada:
/
dalam konten)dalam string $ tmp
Sebuah. gunakan
/
sebagai pembatasATAU
b. gunakan
:
sebagai pembatas (lebih mudah dibaca daripada/
)sumber
Sebenarnya, hal paling sederhana (setidaknya di gnu sed) adalah menggunakan pemisah yang berbeda untuk perintah substitusi sed. Jadi alih-alih s / pattern / '$ mypath' / sedang diperluas ke s / pattern // my / path / yang tentu saja akan membingungkan perintah s, gunakan s! Pattern! '$ Mypath'! yang akan diperluas ke s! pattern! / my / path! Saya telah menggunakan karakter bang (!) (Atau menggunakan apa pun yang Anda suka) yang menghindari potongan garis depan yang biasa, tetapi tidak berarti hanya pilihan Anda sebagai pemisah.
sumber
di mana VAR berisi bidang yang ingin Anda ganti
sumber
Berurusan dengan VARIABEL dalam sed
sumber
Saya memiliki masalah yang sama, saya punya daftar dan saya harus membangun skrip SQL berdasarkan template (yang berisi
@INPUT@
elemen untuk menggantikan):sumber