• 締切済み

1キロバイト文字の削除について

例えばsijisの「、」を削除しようと思い $body =~ s/\xa4//g; とすると\xa4を含む「う」などにも作用し、\xa4を削除してしまいます。 そこで2キロバイトの文字には作用しないようにするにはどうしたらいいか考え 「う」などがあった際には\xa4を削除しないようにしたのですが その場合、例えば「う」と「、」の両方があった時に「、」を削除しなくなってしまいます。 1キロバイトの文字を削除しても2キロバイトの文字には影響しない 何かいいアイデアはないでしょうか?

みんなの回答

  • Tacosan
  • ベストアンサー率23% (3656/15482)
回答No.8

Shift_jis で途中のバイトを指定したときにそれが 1バイト目か 2バイト目かを判断する確実な方法は「先頭から見ていく」ことしかありません (utf-8 なら「先頭バイトか途中のバイトか」は簡単にわかる). したがって #7 のようにすれば動きますが (なぜ添え字を覚えるのかは不明), それは結局 #6 で言われている 「先頭から順番に処理して確実に1バイト目と2バイト目を区別する」 にほかなりません.

  • kumoz
  • ベストアンサー率64% (120/185)
回答No.7

kmee さんのご指摘のとおりでした。失礼しました。 先頭から1バイトずつ見ていく方法は成立するかも? my @byte = split //, $body; my ($i, @idx) = (-1); while (++$i <= $#byte) { if ($byte[$i] =~ /[\x81-\x9F\xE0-\xFC]/) { push @idx, $i, $i + 1; ++$i; } elsif ($byte[$i] ne "\xA4") { push @idx, $i; } } print join('', @byte[@idx]), "\n";

  • kmee
  • ベストアンサー率55% (1857/3366)
回答No.6

>#5さん そう思うでしょ? ところが、その「1バイト目」の文字って、「2バイト目」にも使われるんですよ。 例えば「メ、」(\x83\x81\xa4)だと、「\x81\xa4」なので「、」が残るんですよ。 なので、「全角文字」も「1文字」として扱ってくれるutf8フラグ付き文字列とか、「先頭から順番に処理して確実に1バイト目と2バイト目を区別する」#1にある方法とかが必要になってくるんです。 で、最近のPerl(目安は5.8.6以降)だったら、UNICODE使うのが楽ではないか、と思います。

  • kumoz
  • ベストアンサー率64% (120/185)
回答No.5

直前のバイトが2バイト文字の1バイト目 (\x81~\x9F、\xE0~\xFC) 以外の \xA4 のみを削除してみてはどうでしょうか。 $body =~ s/(?<![\x81-\x9F\xE0-\xFC])\xA4//g; Perl のバージョンが古い場合は、 $body =~ s/([^\x81-\x9F\xE0-\xFC])\xA4/$1/g; とする方法もありますが、先頭にある半角の「、」や「、」が連続してある場合には対応していません。

  • kmee
  • ベストアンサー率55% (1857/3366)
回答No.4

> Jcodeのh2zを用いて、半角、を全角、に変換して全角「、」を削除すれば解決するのでは ○ 元々全角の「、」があった場合、それも削除される ○「、」は\x81\x41なので、例えば「メAB」(\x83\x81\x41\x42)が「ィ」(\x83\x42)に化ける と、結局、問題は解決しません。

  • Tacosan
  • ベストアンサー率23% (3656/15482)
回答No.3

そこまで Unicode を毛嫌いする理由が分からない.... 「宗教上の理由」とか「先祖代々の言い伝え」とかならさておき, そうでないなら Unicode を使うのが手軽だと思うけどなぁ.

  • kmee
  • ベストアンサー率55% (1857/3366)
回答No.2

あと、UTF-8にしたら、\xa4ではないので注意。

  • kmee
  • ベストアンサー率55% (1857/3366)
回答No.1

1キロバイトだと、キロ(k)=1000の意味なので、1000バイトになります。 ○ 最近のバージョンだと、 Encodeモジュールとutf8フラグ付き文字列を使って Encode::decodeでShift_JISからutf8フラグ付き文字列の変換 ↓ 「半角カタカナ」も「全角文字」も「1文字」扱いされるので、通常通りに正規表現を記述 ※ use utf8;して、スクリプトもUTF-8で記述する ↓ Encode::decodeでファイルや画面に出力 ○ Shift_JISのまま処理する場合。 検索したら、次のようなものがありました。 http://homepage1.nifty.com/nomenclator/perl/shiftjis.htm

masa-25
質問者

補足

1バイト文字の間違いでしたね(^-^;ご指摘ありがとうございます。 utf8で処理しないで、Shift-JISのままでどうにかないかと考えていたのです。 Jcodeのh2zを用いて、半角、を全角、に変換して 全角「、」を削除すれば解決するのでは?と思ってます。 まだ試していないので、うまく稼働するか分からないのですが・・・。