X



シェルスクリプト総合 その27
■ このスレッドは過去ログ倉庫に格納されています
0001名無しさん@お腹いっぱい。
垢版 |
2018/05/03(木) 17:54:23.25
シェルスクリプトの総合スレです。
□お約束
・特記なき場合はBourne Shell(/bin/sh)もしくはPOSIX準拠の互換シェルがデフォルトです。
 bash/zsh/ksh/ash/dash/yash/poshなどの専用機能に依存する場合は明示しましょう。
 Linuxユーザは/bin/shの正体がbashまたはdashなので特に注意。
 FreeBSDユーザは/bin/shの正体がashなので注意。
・POSIXについてのリンクは https://en.wikipedia.org/wiki/POSIX にまとめられています
 最新の仕様はこちらへ http://pubs.opengroup.org/onlinepubs/9699919799/
 (左上の「Shell & Utilities」 から参照することができます。)
・v7 shに一番近くて、現役(?)のshは、OpenSolaris由来のheirloom sh。
  http://src.illumos.org/source/xref/illumos-gate/usr/src/cmd/sh/
  http://heirloom.sourceforge.net/sh.html
・csh/tcshのシェルスクリプトは推奨されません。
 (理由は「csh-whynot」でググれ)
・UNIXにはシェルスクリプトに便利な小さなコマンドがいろいろあります。
 manや参考リンクを見ましょう。
 aproposないしはman -kでそれらしい単語による簡単な検索もできます。
・シェルで使えるワイルドカード等は正規表現ではありません。
 正規表現の話題はスレ違い(正規表現スレへ)
・シェルスクリプトのことをシェルってゆうな
□初心者へのアドバイス:
・適した道具を判断するのも頭の重要な使い方。シェルスクリプトよりも
 awkまたはperlの方が適した処理にはそちらを使いましょう。
・知らないコマンドが出てきたらmanを引きましょう。
・思い通りに動かないときは、まずは sh -x でトレースしましょう。
□回答者への注意事項:
・シェルスクリプトでの処理方法を質問しているのに、よくわからずに
 「そういうのはperl使いましょう」と回答するのはやめましょう。
 安易にperlに逃げずにシェルスクリプトで処理するのが頭のいいやり方。
 質問に対して問題が間違ってるといちゃもんをつけるのもやめましょう
前スレ シェルスクリプト総合 その26
https://mevius.5ch.net/test/read.cgi/unix/1489979246/
0349名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:10:50.12
>>343
> 一度全部置換してから読み取ればいいんじゃないですか(名推理

そして一行ずつ読み取るわけですねw

そりゃそうでしょう。\nを全部改行コードに戻してしてしまったら、
区別できないですからね
0352名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:12:08.78
>>347
> だったらお前がそのわけわからんCVS形式でない答えを応えれtばええんちゃんですかね

データの中に改行コードがあるってだけで、
フォーマットは最初から指定してないよ?

その場合どういうやり方があるでしょうって話なんだが、
CSVだと思いこんで効率の悪い方法しか思いつかず
指摘したら逆ギレするのやめなよ?ダサいから
0354名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:13:10.06
>>351
なにが言いたいのかわからんが、RFCのCSVの仕様に改行コードを
エスケープするという仕様はない。ダブルクォートでくくればいいだけ
0359名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:23:33.86
データ | フィルタ | シェルスクリプト(関数なり) | フィルタ > データ
フィルタをどう作るかは具体的じゃないとでCVSしか例にあげてないからCVSなだけなんだが
っていういたって普通のことなのに。そうじゃないナニかを想定しているらしけど、そのナニかの具体的なことは全く言わずに指摘wという否定なだけだもんな
その指摘もトンチンカンなこともあり、ただただ無闇に偉ぶりたいだけにしか見えんなあ
0361名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:25:32.32
>>360
それは最初&最終形態だよ。途中で処理の都合のよいようにするのに仕様もなんもないわっ
マジあほとしか思えない
0362名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:26:22.60
もう一つ解説記事

https://codezine.jp/article/detail/2364

>  改行コードはプラットフォームによって異なります。一般的にWindowsは
> <CR><LF>、UNIXは<LF>です。

>  ※2008/04/16追記:RFCでは末尾(レコードの区切りとして)の改行は
> <CR><LF>を推奨しています。CSVを解釈するプログラムではどちらの
> 改行コードでも読めるように作ることをお勧めします

> ダブルクォートで囲む場合
> "山田","太郎","値に
> 改行や,カンマや""ダブルクォートが含まれても問題ありません。"

> まれにCSVの方言で\エスケープを行うことがあります。
>
>\エスケープを行う特殊な例
>"山田","太郎","値に改行\nや\,カンマや\"ダブルクォートが含まれても問題ありません。"
> この方言はあまり普及していませんので、利用するのは避けましょう。
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
0365名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:28:23.86
CSVスレになってんのはなぜなんだ
勉強にはなるけど
0366名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:28:48.64
もう一つw
https://www.upken.jp/kb/csv.html

> RFC4180準拠
>  基本
>  ヘッダーはあってもなくてもよい
>  空データフィールドがある
>  前後にスペースがあっても無視しない
>  ダブルクォーテーションで囲む場合は同じレコードのすべてのフィールドをダブルクォーテーションで囲む
>  改行、ダブルクォーテーション、カンマを含むフィールドは、ダブルクォーテーションで囲むべき
>  ダブルクォーテーションで囲まれているフィールドでダブルクォーテーションを使用する場合は、ダブルクォーテーションでエスケープする
>  非常に長い文字列を考慮
>  複合パターン
0367名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:29:45.29
>>364
> シェルスクリプトでどう扱うかだぞ?

CSVを扱うという話はしてない
\ でエスケープするのは遅くて無駄という話ならしたがね
0371名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:36:40.96
>>368
CSVの仕様を得意げにーっていうのは

> 因みにCSVはRFCで「内部改行はCRLF」と定まっているので
↑こいつのことですかな?w

まあ、RFCでCRLFと決まってないんですがw
0373名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:39:16.71
>>372
「だいたい」しか「想像」出来てないのに偉そうだなおい
かけないんだろう?だから人にいちゃもんつけるだけなんだろ
いい加減ごめんなさいって言った方がいいぞ?
0374名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:39:21.31
1データの中に改行が含まれてる
そのままだとデータ区切りの改行と見分けがつかない
CSV形式の話はしていない

\nにエスケープする方法では、1データずつ処理しなければならず
外部コマンド呼び出しの必要があるから遅い

ここまでは理解できてんのかなー?
0375名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:39:51.59
>>371
いや、お前のこと。たぶん
それは単に利用できそうなキーポイントでそれを利用してって話でしかないな
たぶん、お前だろうが、得意げには仕様が絶対でどうであれ利用しちゃダメっていう変なヤツ
0377名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:42:26.75
>>373
だいたいの普通の人はその処理方法を想像できる「だいたい」だし、想像=書けるってことなんだが
お前が無闇に絡んでる&お前も具現生ゼロなのになんで謝らなきゃならんのねん
0379名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:45:59.83
今更なんの話かわかってませんっていうのかよw
↓この話だろ。「?」で聞いているところが質問だよ。それぐらいわかれアホ

Excelから出力したCSVのように一行(?)の中に改行が含まれた
データを扱うにはどうしたら良いでしょうか?

もう少し具体的に書きます。

カンマ区切りのCSVデータだと仮定して、
シェルスクリプトの中に関数を一行ごとに呼び出し、
列を引数に対応させたいです。

例えば以下のような内容のファイルがあったとして
a1,a2,a3,a4
b1,b2,b3,b4
c1,c2,c3,c4

syori "a1" "a2" "a3" "a4"
syori "b1" "b2" "b3" "b4"
syori "c1" "c2" "c3" "c4"

という風にsyori関数を呼び出したいのです。

ただし実際には各項目(a1等の部分)にExcelから出力したデータのように
改行やカンマやダブルクォートやシングルクォートや空白が入ることがあるのです
0380名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:50:13.04
何を言っているのだか。最初からCSV形式のデータ扱う話なんかしてないって言っておきながら、前レスではCVSのこと「だけ」のレスなことだから、そのCVSのことだけのことを何を言いたいのかだよ

すでに書いたが、
データ | フィルタ | シェルスクリプト(関数なり) | フィルタ > データ
でしかない。CVSはどうフィルタを書く上では具体的にそれしかでしかないからだけだな

てか、その設問がそんなにきになるならお前が答えろよっw
0381名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:54:06.97
>>380
お前、実際に脳内でどう変換されるか考えてないだろ?
最初のフィルタで\nを全部改行コードにしてしまうと
シェルスクリプトで区別できなくなるんだよ。
0383名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:55:28.23
>>381
はあ????
最初のフィルタでやることは改行コードを他の何かにするに決まってるだろ。なんで逆のことをするねん?さっぱりわからん
0385名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 16:57:43.94
>>383
>改行コードを他の何かに
行端/レコードの終わりでない改行コードだけな。異次元な人なので、行端/レコードの終わりもと思われそうなので、いちおうw
0387386
垢版 |
2018/06/10(日) 17:02:32.48
最 初 の フ ィ ル タ で デ ー タ に 含 ま れ る
改 行 コ ー ド を 他 の な に か に 変 換 す る な ら ば
今度はシェルスクリプトの関数に渡す前に
改行コードに戻さないといけません

でないとこれが実現できません

> syori "a1" "a2" "a3" "a4"
> syori "b1" "b2" "b3" "b4"
> syori "c1" "c2" "c3" "c4"
>
> という風にsyori関数を呼び出したいのです。

なので1データごとに改行コードをもとに戻す処理が必要になります。
すでに指摘してますがforkが発生し遅くなります。
0388名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 17:02:57.65
言質ww
まあ、永遠に「否定だけ」してろ。もうオツムの具合わかったので、いいよ、どう思われようが
0389名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 17:04:45.37
>>385
それを実現するには1データずつ処理 
しなければいけませんね。

デ ー タ 全 体 を 一 気 に 変 換 し よ う と す る と、
区別できないんで
0390名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 17:05:24.55
>>387
言い方が伝わらなかったようで、それは残念。データの改行を他の何かにな。そういう意味での>>386なんだがなあ。まあ、言い方は悪かったかもしれない
で、その指摘はなんらアホな指摘にしかなってません...もう、いいや、勝手にしてくれ
0392名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 17:07:51.94
多分\エスケープ云々は途中でなんらか処理をする時にRFC準拠のエスケープだと不都合だからじゃないかな
「Mika says "I'm Happy"」という文を一つのフィールドとして処理するとき
RFC準拠だと
「Mika says ""I'm Happy""」になるけど、例えばこれをsed(1)やらawk(1)に通したいと思ったときは
「Mika says \"I'm Happy\"」という形にしたほうが処理しやすいでしょう?

そういうことなんじゃないかな。
0394名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 17:09:28.43
>>390
だから デ ー タ の中の改 行を何かに変 換すると
もとに戻す処 理を 一 行 一 行やらない といけないから
遅くなるって指摘をずーっと前にした
その遅く なる理由を思 いつかなかった んだろ?
0397名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 17:17:21.14
>>394
なんで一行一行なんだか。sedかtrでやりゃええことやん。それが一行一行か?
遅くなる遅くなるって遅くなるに決まってるやん。条件によりそれが妥当かどうかなんてなんでそう否定できるのか不思議でならない
んな速度速度言うなら、Cなりでやればって言うw 遅い遅い言うてるけど、お前のもじゃどうすんの?ってのがさっぱりだな
0399名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 17:22:11.92
>>392
> 「Mika says \"I'm Happy\"」という形にしたほうが処理しやすいでしょう?
今の話はもっと複雑で

「Mika says "I'm Happy
'couse picked up \10."」

という文だったらどうするか?って話なんだけどな。
いやわかるよ。どうすればいいかは。
問題はどうやってそれを実現するかって話

sedやawkに通す前に、変換すんの?
0401名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 17:25:37.95
>>397
sedやtrを使うと遅いfork、子プロセス生成が行われるからね
データ量に比例してその回数が増えるやり方は駄目
1回か固定の数回でできるって言うなら話は別だけど
0402名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 17:26:19.38
>>400
最初だけできてもだめ駄目

これが実現できないと駄目

> syori "a1" "a2" "a3" "a4"
> syori "b1" "b2" "b3" "b4"
> syori "c1" "c2" "c3" "c4"
>
> という風にsyori関数を呼び出したいのです。
0404名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 17:48:10.30
思ったんだが
正規表現でやらずに有限状態機械を作って
if ダブルクオートで始まらない
  コンマを探して終了
else
  ""でない"に続くコンマを探して終了

とすれば解決するんじゃないかな。少なくともRFC勧告に則ってるCSVは。
0411名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 20:50:13.84
>>408
後処理のだぞ。そのデータ中の改行と行の区切りの区別をつけるために最初にータ中の改行を処理して、終わったらデータ中の改行を戻すって話だぞ?
少しは処理を想像そしてからなんか言ったら?すごい近視眼で明後日な文句言う前に
0412名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 20:55:32.25
>>409
CSVじゃないからあって言うのもいるけど、だったらデータはどう表すのだろうな
データ中の改行と行の区切りの改行ってわからなくね?そのためにデータの始め終わりを表す何かが必要でそれが何かを言ってないんだったら、それを " として話をしてもおかしくはないってか、それしかないだろう
なんでそんな近視眼なツッコミばかりやねん
0413名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 20:56:07.54
>>282

GNU awk の FPAT を使ってみる。一論理行のデータ数は4個で固定、という前提。

gawk -v RS='\0' -v FPAT='"(([^,\n]*)|(([^"]|\\\\"|\"\")*))"' \
'function syori(v1,v2,v3,v4){ ## ここで何らかの処理 ## }
{
i=1
while(i<NF){
syori($(i++),$(i++),$(i++),$(i++))
}
}' data.txt
0414名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 22:03:59.12
>>411
> 終わったらデータ中の改行を戻すって話だぞ?
そのときに全データの改行を一度に戻すとデータの中の改行と
データ区切りの改行の区別がつかなくなってしまうので、
1データずつ処理する=1行ずつsedなどを実行して遅くなるってことには
気づきましたか?
0415名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 22:29:15.51
>>411
データ中の改行とデータの区切りの改行はどう区別するんだよ。
同じコードだろ。しかもCSVじゃないんだろ?""でくくられてないんだぜ。
0419名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 22:49:09.09
もうそろそろ、安全な文字に変換するというアプローチ
(例えば>>289のようなもの)が
ムダで効率が悪いってことに気づきませんかね?

もう一回煽りますね?

>>323
正直、そういう解答を出してほしかったね。だせるかなーって思っていたけど
シェルスクリプトでそういうデータを扱うなんておかしいとかのたまうばかり
\x1c(ファイル分離)、\x1d(グループ分離)、\x1e(レコード分離)、\x1f(ユニット分離)は
まさにそういう用途で使うもの。ここの連中の技術力の低下を感じる。
0420名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 22:49:14.03
もう一から説明しないと、情報処理の基本すらわかってないようなので
バカバカしすぎだけど、

・改行がデータ中とレコードの終わりを示すのが混在している
・シェルスクリプトは基本、改行は改行でしかなく、データ中なんて知らんただの一行=レコードがブッタ切られる
・データ中の改行を他のナニかに変えれば、シェルスクリプトは一行=1レコードと認識する

前処理:データ中の改行だけをナニかに変える
本処理:改行が終端の一行=1レコードを処理する
後処理:ナニかに変えたのを改行に戻す

たった、これだけのことをなぜ理解できないでトンチンカンなことばっかり言うのか。前処理をsedでできるなんて言ったことないぞ(できるかもだが、それはもっと面倒なの俺は考えんw)。後処理はsedでできることは馬鹿でもわかるだろうにぃぃぃ
0423名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 22:53:10.76
>>420
> 前処理:データ中の改行だけをナニかに変える
> 本処理:改行が終端の一行=1レコードを処理する
> 後処理:ナニかに変えたのを改行に戻す

それは理解しているが、
1. 改行を何かに また 何かを改行にするには、どうやるのか?
2. 変える または 戻す 処理は1コマンドで実行できるのか?

の答えが、1行ずつfork、execしなきゃならないから
データ量に比例して遅くなるって話をしてる
0424名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 22:55:00.78
>>423
お前にじゃねえよ。お前は面倒なのでいいよw
遅い遅い言っていれば。1行ずつfork、execしなくてもいい方法もあるのにそこには考えが及ばないだろうし
0428名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 22:58:11.88
>>426
お前馬鹿だわ
U+001EやU+001Fを区切り文字として利用するんだから
わざわざ改行コードなどを使われない文字に変換する必要ねーだろw
0429名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 22:58:14.56
最初の質問者じゃなかった、何を目的に延々と絡んでるのか意味不明すぎ
できないできないってばかりで
0430426
垢版 |
2018/06/10(日) 22:59:16.28
あ、「安全な文字」っていうのは「通常の用途に使われるけれども日本語圏では滅多に使われない文字」の意味だったのね。
俺の解釈としてはUnicodeに収録されてる四種の区切り文字も「安全な文字」の類に入るからさ。

勘違いしてすまんな
0431名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 22:59:31.44
bash拡張は置換命令あるけど、
POSIXシェルの場合、外部コマンドを呼び出す以外に
置換命令はないんだよ。知ってる?
0432名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 23:03:46.06
>>430
> 俺の解釈としてはUnicodeに収録されてる四種の区切り文字も「安全な文字」の類に入るからさ。
まさに、ぽか〜んだわw
今度はお前にUTF-8の講釈をしないといかんのか?

Unix系で簡単に使えるUnicodeはUTF-8しかないが
(その他のエンコードは、文字の中にNULL文字が入るためシェルスクリプトで扱えない)

そのUTF-8はASCII互換であるため、U+001EやU+001Fは
ASCIIコードの0x1Eと0x1Fと全く同じであるため、
この文脈で、Unicodeかどうかなんて考える必要ないんだよ
0433名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 23:05:23.11
>>428
それは元々のデータがそうであるってこと?そんなんだったら別にこのスレで話題にするようなもんじゃないだろう
いつからそんなのが前提になってるねんwなんかムチャクチャぶりが...ww
0435名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 23:13:46.83
>>433
> それは元々のデータがそうであるってこと?

ちょっと違うな
「元々のデータがそうであってもよい」ってこと

元々のデータ形式について指定はないのだから
(処理するには効率の悪い)CSVデータでもOKだし、
どんなデータでもよい

そのデータ形式も含めて、
どうしたらいいでしょうか?という話だ
0437435
垢版 |
2018/06/10(日) 23:16:17.88
まあ、そのデータもシェルスクリプトで生成はするんだけどな

シェルスクリプト1 → 何らかのデータ形式 → シェルスクリプト2

「何らかのデータ形式」のデータの中に(データ区切りの改行とは別に)
1データの値として改行等が含まれることがあるのでどうすっかなーって話
0438名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 23:16:40.28
>>432
お前は>>323を引用して
> そういう解答を出してほしかった
と言ってるんだろ? UnicodeはASCIIの範囲ではそれと互換なんだからUnicodeかそうじゃないかなんてどうでもいいだろうが
お前が言ってるのは
「フィールド区切りにはカンマやアルメニア文字ではなくそれ専用に用意されている文字種を使いましょうね」
ってことだろ? なんか間違ってる?
「ポカーン」とするのもいいけれど、その前に文章をよく読め。脊髄反射でレスするな。
0439名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 23:17:19.92
>>436
> データの改行とそうじゃない改行をどうすんの?どうやんの?

そこをどうするのが質問だって〜の


> Excelから出力したCSVのように一行(?)の中に改行が含まれた
> データを扱うにはどうしたら良いでしょうか?
って書いてあるんだろ
0445名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 23:21:59.29
>>442
> 初期から出てるだろ

残念 ながら出てない。 \ を安全 な文字に変 換ってことは
つまりデータを 変 換すると言ってる わけだが、
データは 変換(置換)するななってのが
俺の煽ってる内容
0446名無しさん@お腹いっぱい。
垢版 |
2018/06/10(日) 23:22:01.17
>>435
CSVのRFCはフィールド・レコード区切りにU+001F/Eを使えなんて一言も言ってねぇぞ
つーかそれこそコンマと改行が区切り文字ですよと言ってる。
そういうデータを扱うことを議論してる時に、横から偉そうな態度で
「データ区切り専用の文字があるんだから元のデータにそれを使うべき」
なんて言われてもなぁ……。
あなたは論理的思考に弱いようだからもう一度同じことを違う言い方で繰り返すと、
「前提を無視した発言は控えてください」
分かった?
■ このスレッドは過去ログ倉庫に格納されています

ニューススポーツなんでも実況