プロが教える店舗&オフィスのセキュリティ対策術

お世話になっております。
perlでファイルない文字データを抽出する作業をしたいですが、やり方が分からなくて、ご存知の方ぜひ教えて頂けばと思います。
001.html内の内容
<html>
<head>
</head>
<body>
テキストテキストテキストテキストテキストテキストテキストテキストテキストテキスト<img src="aaa" \/>テキストテキストテキストテキストテキストテキストテキストテキスト<img src="bbb" \/><img src="ccc" \/><img src="aaa" \/>テキストテキストテキストテキストテキストテキストテキストテキスト</body>
</html>

質問内容

(1)このなかの<img src="aaa" \/>イメージファイル名を抽出したいです。本文ではイメージファイルの拡張子はなしです。入力の間違いではないです。
(2)抽出した文字列をimg.txtファイルで出力


以上よろしくお願いします。

A 回答 (5件)

ちと気になった点を突っ込ませてくださいな>#4.


my $html = join("", <IN>);
よりは
$/ = undef; my $html = <IN>;
の方がよいかと. あと,
printf(OUT "%s\n", join("\n", @src));

$" = "\n"; print OUT "@src\n";
にした方がシンプルじゃないかな.

あと open は (それなら) 3引数にするとか, そもそもリダイレクト (とコマンドライン引数) にまかせた方が簡単とかありますけどね.
    • good
    • 0
この回答へのお礼

ご回答ありがとうございました。
頂いた内容で推進させて頂きたいと思います。

お礼日時:2010/12/22 10:21

こんな感じですかね。


コードを見比べてみてください。
インデントは全角スペースになっています。


#!/usr/bin/perl
use strict;

open(IN, "001.html") or die "ファイルが開けない";
open(OUT, "> img.txt") or die "ファイルが開けない";
my $html = join("", <IN>);

my @src = ($html =~ /<img[^>]+src="(.+?)"/g);
@src = &uniq(@src);
printf(OUT "%s\n", join("\n", @src));

sub uniq {
 my %h;
 return grep{
  if(not defined $h{$_}){
   $h{$_} = 1;
   1;
  }
 } @_;
}
    • good
    • 0
この回答へのお礼

ご回答頂きまして誠にありがとうございました。
皆さまから教えて頂いた案を参考した上、何とかクリアできました。

今後ともよろしくお願いします。

お礼日時:2010/12/22 14:48

「部分しか抽出できなかった」「上手くいけなかった」と書かれていますが, これでは何がどう「部分しか抽出できなかった」「上手くいけなかった」のかが分かりません.


・どのような入力に対して
・どのような結果を期待して
・(その期待に反し) 実際の結果はどうであったのか
をきちんと書いてください.

前半は「少なくとも方針はあっている」と思います. 後ろの方は何を表示させたいのかわかりませんが.
    • good
    • 0
この回答へのお礼

度々お手数おかけしまして申し訳ございませんでした。

お礼日時:2010/12/22 14:49

「やり方が分からなくて」ということだから「やり方」だけ:


1. ファイルを読み込む. $/ を undef にしてから読み込むとファイル全体を一気に読み込めて楽 (だけどメモリが足りなくなったら知らない).
2. その中から img タグを取り出す. 正規表現を使うのが自然か.
3. さらに「イメージファイル名」を取り出す. ここもやっぱり正規表現を使うところだろう.
4. 必要な「イメージファイル名」を出力.

ちなみに重複したものを 1つにまとめるのはハッシュを使うのがセオリー.

この回答への補足

ご回答ありがとうございました。
以下のように抽出だけできるかどうかを書いてみました
use strict;

my $temp="";

while(<>){
my $line=$_;

if($line=~/<img src="(.*?)" \/>/){
my $img=$1;
$temp .= "$img\n";
}
}
print $temp;
部分しか抽出できなかったのはどこか間違っているでしょうか?
また重複を避けるperlも書いてみましたが上手くいけなかった
use strict;

my $Key="";
my %Buf=();

while(<>){
my $line=$_;

# キーが含まれている行なら
if ( $line =~ /<img src="(.*?)">$/ )
{
$Key = $1;
if ( defined( $Buf{ $Key } ) )
{
next;
}

print $line;

$Buf{ $Key }++;
}
else
{
print $line;
}
}

補足日時:2010/12/21 15:26
    • good
    • 0
この回答へのお礼

目的はっきり言わなくて申し訳ございませんでした

お礼日時:2010/12/22 14:50

(1) 「このなかの<img src="aaa" \/>イメージファイル名を抽出したいです」とはどういうことでしょうか? 特に「イメージファイル名」が何 (どこ) を意味するのか分かりません. あと, / の前に変なものが入ってるんだけどそれも本当にあるの?


(2) 「img.txtファイルで出力」とは? 「img.txt ファイル『に』出力」ですか?

この回答への補足

(3)抽出されたイメージファイル名が重複された場合は1つだけ残す。

補足日時:2010/12/21 12:59
    • good
    • 0
この回答へのお礼

ご回答ありがとうございます。

>(1) 「このなかの<img src="aaa" \/>イメージファイル名を抽出したいです」とはどういうことでしょうか? 特に「イメージファイル名」が何 (どこ) を意味するのか分かりません. あと, / の前に変なものが入ってるんだけどそれも本当にあるの?
<img src="aaa" \/>⇒<img src="aaa" />となります。
作業の目的はhtmlに使われているファイルとイメージフォルダ内ファイルが一致しているかどうかをチェックするため、html内イメージファイルを抽出したいのです。
>(2) 「img.txtファイルで出力」とは? 「img.txt ファイル『に』出力」ですか?
「img.txt ファイル『に』出力」したいです。

下手な日本語で申し訳ございませんでした。
よろしくお願いします。

お礼日時:2010/12/21 12:11

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!