web-dev-qa-db-ja.com

awkステートメント内でアポストロフィをエスケープするにはどうすればよいですか?

Ubuntu Linuxとbashシェルを使用しています。 awkステートメント内でアポストロフィをエスケープするにはどうすればよいですか? awkを使用してファイルからデータを抽出した後、SQLを出力したいので、次のようにします。

awk -F',' '{print "SELECT * from user where id = '"$2"';"}' myfile.csv

しかし、これは出力のみです:

SELECT * from user where id = ;

上記を変更すると

awk -F',' '{print "SELECT * from user where id = "$2";"}' myfile.csv

その後、私は次のような文を取得します

SELECT * from user where id = cf915247dfcf47b6814b5350e5cbdfd8;

しかし、必要なidの周りに一重引用符はありません。

4
Dave

次の2つの方法でこれにアプローチできます。

  1. 変数を介して一重引用符を渡します。

    awk -v sq="'" -F',' '{print "SELECT * from user where id = "sq$2sq";"}' myfile.csv
    
  2. Printfステートメントで単一引用符の16進値を使用します。

    awk -F',' '{printf "SELECT * from user where id = %c%s%c;\n",0x27,$2,0x27}' myfile.csv
    
2

文字列内で \47を使用する (または\047)を使用できます。awk'を意味します。

awk -F, '{print "SELECT * from user where id = \47" $2 "\47;"}' myfile.csv

それは一種の優雅ではありません(「繰り返される magic value '47'は何ですか?!」)が、構文は簡潔で、この単一引用符の作成方法は pretty - well既知

awk\47を特別に扱うものであり、シェルではありません。 ''- quoted文字列では、BashのようなBourneスタイルのシェル any展開を実行しないtcshのようなCシェルは行いますが、\47を展開せず、これは引き続き機能します。

\047の代わりに\47を使用することもできます。\47の直後に続かない限り、両方とも機能します8進数(0〜7)。この場合、\047を使用して、誤った文字を示すことを避ける必要があります。一部の言語とは異なり、47\47は、先頭の0がなくても8進数であることに注意してください。下記参照。

\47はどういう意味ですか? そのように\47を使用するときに、なぜこれは0x27を使用するのですか?

これは、2人の16人が4つの8人を作るからです。

  • \47octal 文字シーケンスであるため、4×8 + 7×1 = 39です。
  • 0x27hexadecimal 数値リテラルであるため、2×16 + 7×1 = 39です。
    次に、printf%c指定子は、それを文字としてフォーマットします。

python -c 'print int("47", 8), int("27", 16)'で確認すると、期待どおり39 39が得られます。

1
Eliah Kagan

おかしくなりそうですが、ここに行きます:

awk -F',' '{print "SELECT * from user where id = '"'"'" $2 "'"'"'" ";"}' myfile.csv

SELECT * from user where id = 'cf915247dfcf47b6814b5350e5cbdfd8';

お役に立てれば!

1
Terrance