日付を使用して列を変換してcsvファイルに追加する

日付を使用して列を変換してcsvファイルに追加する

最初の列には、日付/時刻を表す文字列を含むCSVがあります。追加の列を追加し、日付/時刻をエポックに変換したいと思います。
私は以下を試しました:

awk -F "," 'BEGIN{ OFS="," } {$14=$(date -jf "%m/%d/%Y %H:%M:%S %p" $1 "+%s"); print}’ mycsv.csv > test  

私は得る:

awk: illegal field $(0%m/%d/%Y %H:%M:%S %p"1/30/2017 11:14:55 AM"+%s), name "(null)"
 input record number 1, file mycsv.csv
 source line number 1  

このフィールドの日付変換が機能することがわかっているため、いくつかの構文エラーが発生します。
私がしたいことはどうすればいいですか?

答え1

私はGNUを持っているdateので、コマンドラインオプションは異なります。しかし、問題はawkの構文のようです。$(...)awkスクリプトではシェルサブプロセス設定を使用できません。system()文字列を渡す関数が必要です。したがって、有効なシェルコマンドをawk文字列として設定する必要があり、それをawkスクリプト内でシステムに渡すことができます。

このような:

awk -F "," 'BEGIN{ OFS="," } {$14=system("date -jf \"%m/%d/%Y %H:%M:%S %p\" \""$1"\" \"+%s\""); print}' mycsv.csv > test

またはより良い読みやすさのために

awk -F "," '
  BEGIN{ OFS="," }
  {
    $14 = system("date -jf \"%m/%d/%Y %H:%M:%S %p\" \"" $1 "\" \"+%s\"");
    print
  }' \
  mycsv.csv > test

答え2

awkGNU(私の意見ではOSXで動作する必要があると思う)がある場合は、システムに依存するのではなくbrew内部GNUを使用できます。mktimestrftimedate

残念ながら、入力形式は次の形式ではありません。日付仕様必要な形式mktimeなので、時間文字列を一部分割して再配置する必要があります。例えば、与えられた

$ cat file.csv 
09/23/2016 11:12:19 AM,field2,field3

それから

gawk -F, '
  {
    split($1,a,/[/: ]/);
    ts = sprintf("%4d %02d %02d %2d %2d %2d", a[3], a[2], a[1], a[7] ~ /^[Pp]/ ? a[4]+12 : a[4], a[5], a[6]); 
    $0 = strftime("%s", mktime(ts)) FS $0
  } 1' file.csv
1510243939,09/23/2016 11:12:19 AM,field2,field3

答え3

Miller(mlrmacOSでHomebrewを介してパッケージとして利用可能miller)を使用し、入力がヘッダーなしのCSVファイルであり、フィールド1のフォーマットされた日付を解析してフィールド14にUnixタイムスタンプを書き込もうとします。

mlr --csv -N put '$14 = strptime($1,"%m/%d/%Y %H:%M:%S %p")' mycsv.csv

ヘッダーがある場合は、その-Nオプションを削除し、数値フィールドの代わりに名前付きフィールドを使用します(例:)$timestamp = strptime($date, ...)

このstrptime()関数は提供されたパターンを使用してフォーマットされた日付を解析し、Unixタイムスタンプを返します。

質問に記載されている日付の場合、UTCタイムゾーンにあると仮定すると、新しいフィールドの値はです1485774895.000000。ローカルタイムゾーンを考慮するには、strptime_local()代わりにを使用してくださいstrptime()。 Unixタイムスタンプの整数部分だけが必要な場合は呼び出しstrptime()int(...)

関連情報