• ベストアンサー
※ ChatGPTを利用し、要約された質問です(原文:Perlの正規表現)

Perlの正規表現で特定の文字列を抜き出す方法は?

このQ&Aのポイント
  • Perlの正規表現についての質問です。特定の文字列を抜き出す方法について教えてください。
  • 上記の例では、「^^^^^」という特定の文字列を抜き出したいとのことですが、正規表現ではどのように記述すればよいのでしょうか。
  • if文を二つ書かずに、抜き出した順に特定の文字列を出力する方法を教えてください。

質問者が選んだベストアンサー

  • ベストアンサー
  • sakusaker7
  • ベストアンサー率62% (800/1280)
回答No.5

>もうひとつ教えてほしいのですけど、抜き出した値が200.000や-12.000 整数部分が一桁に限らないということですね。 \d\.\d+ -?\d\.\d+ の \. の前の部分が整数部分の数字になります。 現状でそこは \d つまり数字一つしか想定していないのでここを 複数の数字を受け付けるようにすればOKです。 つまり、 \d+\.\d+ もしくは \d*\.\d+ のようになります。これは、前者は整数部に必ず数字がなければいけませんが 後者は .1828459 のようなものも受け付けます。

WCCF2008
質問者

お礼

ありがとうございました。 抜き出せました。 このたびは、不快な気持にさせたにも関わらず、 ご親切にアドバイスいただきまして、本当に助かりました。

その他の回答 (4)

  • sakusaker7
  • ベストアンサー率62% (800/1280)
回答No.4

> 5.8に書き換えて、実行してみまたところ、マッチングエラーが出ました。 if($_ =~ /Alt \s+ \d+ \s+ (\d\.\d+) [^\d-]+ (-?\d\.\d+))/; print OUT "$1," ; これはわたしの例示した正規表現がどうこうじゃなくて、質問者さんのif文の書き方が悪いだけですけど なぜにそこまで面倒見なければならないのですか? if($_ =~ /Alt \s+ \d+ \s+ (\d\.\d+) [^\d-]+ (-?\d\.\d+)/x) { print OUT "$1," ; }

WCCF2008
質問者

補足

sakusaker7様 >これはわたしの例示した正規表現がどうこうじゃなくて、質問者さんのif文の書き方が悪いだけですけど >なぜにそこまで面倒見なければならないのですか? 私のif文がまずいのはわかった上でアドバイスを頂きたかったのです。文章の書き方よくなかったようです。すいません。 もうひとつ教えてほしいのですけど、抜き出した値が200.000や-12.000 の際も抜き出せるようにするにはどのような正規表現にすればよろしいのでしょうか? 何卒、よろしくお願いします。

  • sakusaker7
  • ベストアンサー率62% (800/1280)
回答No.3

5.10固有の機能(ここでは say)を使うために、これまた 5.10固有の featureを使っています。 5.8とかでやるのなら、sayを printに置き換えてください(末尾の改行は自分で付加)。 あるいは Perl6::say モジュールを入れてもよいです。

WCCF2008
質問者

補足

アドバイスありがとうございます。 5.8に書き換えて、実行してみまたところ、マッチングエラーが出ました。 Unmatched [ in regex; marked by <-- HERE in m//Alt \s+ \d+ \s+ (\d\.\d+) [^\d-]+ (-?\d\.\d+)) #################################################### #!/bin/perl open(LOG,"<$ARGV[0]"); #FileOpen open(OUT,">$ARGV[0].csv"); while (<LOG>) { if($_ =~ /Alt \s+ \d+ \s+ (\d\.\d+) [^\d-]+ (-?\d\.\d+))/; print OUT "$1," ; } } close(OUT); すみませんが再度アドバイスを頂きたく、よろしくお願いします。

  • sakusaker7
  • ベストアンサー率62% (800/1280)
回答No.2

なんか頭が痛くなる正規表現ですね 何でもかんでも () で囲むから、どれが必要なパターンなのかわかりにくいし (\s+)+ のようにカッコの中の最後が繰り返しで、外側にすぐまた繰り返しというのは 意地悪な入力を食わせたときにバックトラックの回数が爆発する可能性があるので 基本的には禁じ手です。 で、 899 YES Alt 0 0.000 pps 2.000 pps 4.000 pps 0 2 YES Alt 0 1.222 (space)-0.100 (space)3.000(space)0 103 NO Alt 0 3.333 % 0.000 % 0.000 % 0 から、 2.000 -0.100 0.000 を抜き出したいということと、(space)が一個以上のスペースだとすると 数値の部分の表現は多少修正するとしても use strict; use feature ':5.10'; while (<DATA>) { chomp; say; /Alt \s+ \d+ \s+ (\d\.\d+) [^\d-]+ (-?\d\.\d+)/x; say "$1 : $2"; } __END__ 899 YES Alt 0 0.000 pps 2.000 pps 4.000 pps 0 2 YES Alt 0 1.222 -0.100 3.000 0 103 NO Alt 0 3.333 % 0.000 % 0.000 % 0 こんな感じで取れるんじゃないでしょうか。 実行結果: 899 YES Alt 0 0.000 pps 2.000 pps 4.000 pps 0 0.000 : 2.000 2 YES Alt 0 1.222 -0.100 3.000 0 1.222 : -0.100 103 NO Alt 0 3.333 % 0.000 % 0.000 % 0 3.333 : 0.000 そもそも区切りがどうとか考えないで、数値の部分だけまとめて取り出せばいいような。 my @f = /(-?\d\.\d+)/xg; say join(' : ', @f); 0.000 : 2.000 : 4.000 1.222 : -0.100 : 3.000 3.333 : 0.000 : 0.000

WCCF2008
質問者

お礼

回答ありがとうございます。 ご回答いただいた表現について、初心者の私には理解するには 難しい箇所もございますが、確認してみます。

WCCF2008
質問者

補足

sakusaker7さま 教えて頂いた記述を実行してみたのですが、 Can't locale feature.pm in @INC(@INC contains: C:/perl/lib C:/perl/site/lib .) at test.pl line2 . BEGIN failed--compilation aborted at test.pl line 2. とエラーになります。 verの問題なんでしょうか?アドバイスをお願いします。

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

その (space) というのは何を表していますか? 各行の正確なフォーマットと「どこを取り出したいのか」を書いてもらえませんか?

WCCF2008
質問者

補足

ご質問の件について、回答します。 sakusaker7様のご回答がそのままなのですが 899 YES Alt 0 0.000 pps   2.000  pps   4.000 pps    0 2  YES Alt 0 1.222 (space)-0.100 (space) 3.000(space) 0 103 NO Alt 0 3.333 %    0.000 % 0.000 %   0 から、 2.000 -0.100 0.000 を抜き出したいということ。 (space)が一個以上のスペース(空白)を意味します。 以上でございます。

関連するQ&A