CSVファイルの読み取り中に最終値の後続の二重引用符を印刷することはできません。

CSVファイルの読み取り中に最終値の後続の二重引用符を印刷することはできません。

.csvファイル(Googleシートで作成され、ローカルコンピュータにダウンロードされた)行をJavaScriptオブジェクトに変換しようとしています。最後の二重引用符の印刷を拒否する最後のフィールドを除いて、すべてのフィールドを正しく出力できます。また、端末の出力で末尾の「]」が誤って配置され、「comps」行の先頭(末尾の代わりに)に配置されました。最後に二重引用符が正しく印刷されないのはなぜですか?

#! /usr/bin/env bash

list_file="input.csv"
destination_file="output.js"

IFS=","

while read field1 field2 field3 field4 field5 field6 field7 field8 field9 field10 field11 field12 field13 field14
do
    echo '"'${field8}'": { r: "'${field2}'", g: "'${field3}'", b: "'${field4}'", hex: "'${field5}'", code: "'${field1}'", 
    desc: "'${field9}'",
    comps: ["'${field10}'", "'${field11}'", "'${field12}'", "'${field13}'", "'${field14}'"]
    },' >> $destination_file
done < $list_file

echo "};" >> $destination_file

出力の1行は次のとおりです。

"#288": { r: "x", g: "x", b: "x", hex: "x", code: "XXXX", 
    desc: "description here",
"], comps: ["#1", "#2", "#3", "#4", "#5
    },

3行目には、最後の二重引用符と閉じ括弧が最初に印刷されます。

また、各個々のフィールドをテストするときは、次を使用してください。

echo '"' $field14 '"'

最後のフィールドに対してのみ同じ出力を取得します(閉じる二重引用符なし)。ただし、他のすべてのフィールドは期待どおりに印刷されます。

ベストアンサー1

Shellは、テキストとデータの処理における恐ろしい言語です。シェルの使命は、タスク自体を実行するのではなく、タスクを完了するために(そしてかなり上手に)他のプログラムの実行を調整することです。テキスト(およびCSV)の処理に適した言語を使用してください。たとえば、パールは次のようになります。

$ cat csv-to-js.pl 
#!/usr/bin/perl

use strict;
use Text::CSV qw(csv);

my $fmt = <<__EOF__;
"%s": { r: "%s", g: "%s", b: "%s", hex: "%s", code: "%s",
    desc: "%s",
    comps: ["%s", "%s", "%s", "%s", "%s"],
    },
__EOF__

# default to reading stdin if no args are supplied
push @ARGV, '/dev/stdin' unless (@ARGV);

my $csv = Text::CSV->new();

foreach my $f (@ARGV) {
  open my $fh, "<", $f or die "$f: $!";
  while (my $row = $csv->getline($fh)) {
    printf $fmt, @$row[7,1..4,0,8,9..13]; # perl arrays start from 0, not 1
  };
  close $fh;
}

これは以下を使用します。テキスト::CSVCore Perlに含まれていないモジュールは別途インストールする必要があります。 Debian、Ubuntu、Mintなどの派生製品ではsudo apt-get install libtext-csv-perlcpan

スクリプトはprintfのフォーマット文字列を作成し、コマンドラインにリストされているCSVファイルを開き、各行を読み取って解析し、printfを使用して印刷します。

ちなみに、このスクリプトは、行がUnixテキストファイル(LF)で終わるのか、CR / LF(dos / windowsテキストファイル)で終わるかに関係なく機能します。

入力例:

$ cat input.csv 
XXXX,x,x,x,x,6,7,"#288","description here","#1","#2","#3","#4","#5"
YYYY,x,x,x,x,6,7,"#289","another description here","#1","#2","#3","#4","#5"
ZZZZ,x,x,x,x,6,7,"#290","and another description here","#1","#2","#3","#4","#5"

サンプル実行:

$ ./csv-to-js.pl input.csv 
"#288": { r: "x", g: "x", b: "x", hex: "x", code: "XXXX",
    desc: "description here",
    comps: ["#1", "#2", "#3", "#4", "#5"],
    },
"#289": { r: "x", g: "x", b: "x", hex: "x", code: "YYYY",
    desc: "another description here",
    comps: ["#1", "#2", "#3", "#4", "#5"],
    },
"#290": { r: "x", g: "x", b: "x", hex: "x", code: "ZZZZ",
    desc: "and another description here",
    comps: ["#1", "#2", "#3", "#4", "#5"],
    },

おすすめ記事