コメント(#で始まる)とVARIABLE=値の行だけを含む単一の入力ファイルで、見つかった場合には単一の変数の値を置き換え、見つからなかった場合にはペアをファイルの最後に追加することは可能でしょうか?
私の現在の方法は、1パス目で削除して2パス目でファイルの最後に追加するという方法で動作しますが、この方法だと行順がぐちゃぐちゃになってしまいます(しかも2種類のコマンドになっています)
sed -r "/^FOOBAR=.*$/d" -i samefile &&
sed -r "$ a\FOOBAR=newvalue" -i samefile
これを行う方法はないのでしょうか?もし他のユーティリティ (awk, ….) がこれを行うならば、私は sed よりもそれを利用したいと思います
39 None 2013-05-02
sed
では、実際には非常に簡単です: 一致する行があれば、それをh
古いスペースにコピーし、s
値を置換します。 la$
t行のex
ホールドスペースとパターンスペースを変更し、後者が空かどうかをチェックします。もし空でなければ、すでに置換が行われているので何もしなくてもよいことを意味します。もし空であれば、それはマッチするものが見つからなかったことを意味するので、パターンスペースを希望の変数=値に置き換えて、ホールドバッファの現在の行に追加します。最後に、ex
を再度変更します
sed '/^FOOBAR=/{h;s/=.*/=newvalue/};${x;/^$/{s//FOOBAR=newvalue/;H};x}' infile
上記はgnu sed
の構文です。ポータブルです
sed '/^FOOBAR=/{
h
s/=.*/=newvalue/
}
${
x
/^$/{
s//FOOBAR=newvalue/
H
}
x
}' infile
34 don_crissti 2015-09-22
これはたぶん短縮できると思います。単発のsedコマンドではなく、grepも使っていますが、基本的にはこれでいいようです。単行で、その場で編集してくれます(テンポラリファイルはありません)
grep -q "^FOOBAR=" file && sed "s/^FOOBAR=.*/FOOBAR=newvalue/" -i file ||
sed "$ a\FOOBAR=newvalue" -i file
18 snapshoe 2013-05-02
sed
sed
hold space
を扱うのは簡単ではないと思うので、ここではよりシンプルな sed
のアプローチを紹介します。hold space
に慣れているのであれば、don_crissti のアプローチを使うことで、既存の行から何かを保存する機会を増やすことができますが、通常、これは非常にまれです
この方法では、落としたい行以外をすべて印刷して、最後に置き換えを追加します
sed -n -e '/^FOOBAR=/!p' -e '$aFOOBAR=newvalue' infile
16 haridsv 2016-11-16
他の回答に基づいて、変数がファイルに存在する場合は変数の値を置換し、存在しない場合はファイルの最後に追加します(投稿されているsed
コマンドが行うこととは異なります)
perl -ne '$c=1 if s/^FOOBAR=.*$/FOOBAR=newvalue/;
print;
END{print "FOBAR=newvalue" unless $c==1}' file > tmpfile &&
mv tmpfile file
3 terdon 2013-05-02
場内編集」は自動ではありませんが、awkでは少し楽になりました
awk -v varname="FOOBAR" -v newval="newvalue" '
BEGIN {FS = OFS = "="}
$1 == varname {$2 = newval; found = 1}
{print}
END {if (! found) {print varname, newval}}
' file > tempfile &&
mv tempfile file
1 glenn jackman 2013-05-02
空のレコードを作成するには、grep
とecho
を使用するだけです
grep -q '^FOOBAR=' somefile || echo 'FOOBAR=VALUE' >> somefile
sed -i 's/FOOBAR=.*$/FOOBAR=VALUE/' somefile
各行はエラーコードゼロでエスケープされます
1 MUY Belgium 2016-03-08
実際には以下のように動作します。 sed -i '/^FOOBAR=/{h;s/=.*/=newvalue/};${x;/^$/{s//FOOBAR=newvalue/;H};x}' infile
選択された答えの中に-iがありません
0 Yogesh Kamat 2016-04-22
を使ってPerlでこれを行い、インプレースではこれで問題なく動作するようになりました
grep ^FOOBAR= my.file && perl -i -ple "s/^FOOBAR=.+/FOOBAR=newvalue/g" my.file || echo FOOBAR=newvalue >> my.file
-1 antweiss 2015-10-29