13

現在、Jsoupを使用して、サード パーティの Web ページから特定の情報 (すべてのテキストではない) を抽出しています。定期的に行っています。これは、特定の Web ページの HTML が変更されるまで問題なく機能します。この変更は、既存の Java コードの変更につながります。これらの Web ページは非常に頻繁に変更されるため、これは面倒な作業です。また、プログラマーが Java コードを修正する必要があります。これは、ウェブページで私が興味を持っている HTML コードの例です。

<div>
<p><strong>Score:</strong>2.5/5</p>
<p><strong>Director:</strong> Bryan Singer</p>
</div>
<div>some other info which I dont need</div>

ここで私がやりたいことは次のとおりです。この Web ページ (HTML ファイル) をローカルに保存し、そこから次のようなテンプレートを作成します。

<div>
<p><strong>Score:</strong>{MOVIE_RATING}</p>
<p><strong>Director:</strong>{MOVIE_DIRECTOR}</p>
</div>
<div>some other info which I dont need</div>

Web ページの実際の URL とともに、これらの HTML テンプレートは Java プログラムへの入力となり、これらの定義済みキーワード ( {MOVIE_RATING}{MOVIE_DIRECTOR}など) の場所を見つけ、実際の Web ページから値を抽出します。

この方法では、Web ページが変更されるたびに Java プログラムを変更する必要はありません。Web ページの HTML を保存し、データをこれらのキーワードに置き換えるだけで、残りはプログラムによって処理されます。たとえば、将来、実際の HTML コードは次のようになります。

<div>
<div><b>Rating:</b>**1/2</div>
<div><i>Director:</i>Singer, Bryan</div>
</div>

対応するテンプレートは次のようになります。

<div>
<div><b>Rating:</b>{MOVIE_RATING}</div>
<div><i>Director:</i>{MOVIE_DIRECTOR}</div>
</div>

また、これらの種類のテンプレートの作成は、プログラマーでなくても、ファイルを編集できる人なら誰でも行うことができます。

問題は、Javaでこれをどのように達成できるかということです。この問題に対する既存のより良いアプローチはありますか?

注: グーグルでいくつかの研究論文を見つけましたが、それらのほとんどは事前の学習データを必要とし、精度も懸念事項です。

4

6 に答える 6

4

あなたが与えたアプローチは、正規表現の部分を除いてギルバートのものとほとんど同じです。私は醜い正規表現の世界に足を踏み入れたくありません.価格、製品仕様の抽出など、映画情報以外の多くの分野でテンプレートアプローチを使用することを計画しています.

  1. あなたが説明するテンプレートは、実際には通常の意味での「テンプレート」ではありません。一連の動的コンテンツが挿入された状態で出力にダンプされるセットの静的コンテンツです。代わりに、これはテンプレートの「逆」です。これは、必要なパラメーターを見つけたままにして、丸呑みして破棄する解析パターンです。

  2. Web ページは定期的に変更されるため、コンテンツをハードコーディングして正確に解析するのではなく、前提条件を最小限にして、本質的な機能に「ズームイン」したいと考えています。つまり、"Rating:" などの文字どおり一致するキー テキストにコミットし、インターリーブ マークアップを"<b/>"はるかに柔軟な方法 (無視して壊れずに変更できるようにする) で扱いたいとします。

  3. (1) と (2) を組み合わせると、結果に好きな名前を付けることができますが、正規表現を使用して解析します。つまり、テンプレート アプローチは、正規表現を使用した解析アプローチです。これらはまったく同じものです。問題は、正規表現はどのような形式を取るべきかということです。

    3A。Java ハンドコーディングを使用して解析を行う場合、明らかな答えは、正規表現形式が形式であるべきだということjava.util.regexです。それ以外のものは開発の負担であり、「非標準」であり、保守が困難になります。

    3B. html 対応のパーサーを使用する場合は、jsoup が適切なソリューションです。問題は、jsoup が提供しているように見えるよりも多くのテキスト/正規表現の処理と柔軟性が必要なことです。特定の html タグと構造にロックされすぎているように見えるため、ページが変更されると壊れます。

    3C。ANTLR などのはるかに強力な文法制御の汎用テキスト パーサーを使用できます。構文解析を制御するために backus-naur にヒントを得た文法が使用され、解析されたデータを処理するためにジェネレーター コードが挿入されます。ここで、構文解析式は、ページ上でのテキストの順序付けや、テキスト フィールドと値の相互関係に関する複雑なルールを使用して、非常に強力な場合があります。あなたは言語を処理していないので、パワーはあなたの要件を超えています. そして、マークアップ タグなど、スキップする醜いビットを記述する必要があるという事実を逃れることはできません。また、初めて ANTLR と格闘する場合、生産性を回収する前に教育投資が必要になります。

    3D。シンプルなテンプレートタイプのアプローチを使用して簡単な答えを出すJavaツールはありますか? まあ、グーグル検索はあまり希望を与えませんhttps://www.google.com/search?q=java+template+based+parser&ie=utf-8&oe=utf-8&aq=t&rls=org.mozilla:en-GB :official&client=firefox-a . このような野獣を作成しようとする試みは、基本的な正規表現解析またはより高度な文法制御された解析のいずれかに退化すると思います。テキストの一致/無視/置換の基本的な要件が解決策をそれらの方向に駆り立てているからです。それ以外は単純すぎて実際に機能しません。否定的な見方で申し訳ありません-それは問題のスペースを反映しているだけです.

私は (3A) を、ニーズに対する最もシンプルで強力かつ柔軟なソリューションとして支持します。

于 2013-03-11T01:31:22.920 に答える
2

ここでは実際にはテンプレート ベースのアプローチではありませんが、 Selectorクエリを構成ファイルに外部化するだけであれば、jsoup は実行可能なソリューションになる可能性があります。

プログラマーでない人は HTML を見る必要さえありません。構成ファイルのセレクターを更新するだけです。SelectorGadgetのようなものを使用すると、実際に使用するセレクターを簡単に選択できます。

于 2013-03-07T02:54:32.170 に答える
1

または、テンプレートの代わりに「ルール」と呼ぶものを使用して、別のアプローチを試すこともできます。ページから必要な情報ごとに、テキストを抽出する jQuery 式を定義できます。多くの場合、ページの変更が少ない場合、適切に記述された同じ jQuery 式でも同じ結果が得られます。

次に、Jerry (Java では jQuery) をほぼ同じ式で使用して、探しているテキストを取得できます。したがって、セレクターだけでなく、DOM ツリーをウォーク/フィルター処理するための他の jQuery メソッドもあります。

たとえば、一部のDirectorテキストのルールは次のようになります (一種の sudo-java-jerry-code で):

$.find("div#movie").find("div:nth-child(2)")....text();

ルールには、複数の行にまたがる、より多くの (そしてより複雑な) 式が存在する可能性があります。たとえば、いくつかのノードを反復するなどです。

あなたがオブジェクト指向の人であれば、各ルールは独自の実装で定義できます。あなたがグルーヴィーな人なら、プロジェクトを再コンパイルせずに、必要に応じてルールを書き直すことさえできます。等。

ご覧のとおり、ここでの核となる考え方は、テキストを見つける方法のルールを定義することです。マイナーな変更には脆弱である可能性があるため、パターンに一致しないようにします-2つのdivの間にスペースが追加されている場合を想像してください:)。この例では、ルールを定義するために jQuery に似た構文 (実際には Jerry に似た構文です。これは Java を使用しているためです) を使用しています。これは、jQuery が人気がありシンプルであり、Web 開発者にも知られているためです。最後に、独自の構文を定義できます (使用している解析ツールによって異なります): たとえば、HTML を DOM ツリーに解析し、ヘルパー メソッドを使用して、目的の場所までトラバースする方法を記述することができます。Jerry を使用すると、下にある DOM ツリーにもアクセスできます。

お役に立てれば。

于 2013-03-07T21:04:19.197 に答える
1

Javaでこれを達成するにはどうすればよいですか?この問題に対する既存のより良いアプローチはありますか?

テンプレート アプローチは優れたアプローチです。あなたはあなたの質問ですべての理由を述べました。

テンプレートは、処理したい HTML だけで構成され、他には何もありません。これがあなたの例に基づく私の例です。

<div>
<p><strong>Score:</strong>{MOVIE_RATING}</p>
<p><strong>Director:</strong>{MOVIE_DIRECTOR}</p>
</div>

基本的に、Jsoup を使用してテンプレートを処理します。次に、Jsoup を使用して Web ページを処理するときに、処理されたすべてのテンプレートをチェックして、一致するものがあるかどうかを確認します。

テンプレートの一致では、処理されたテンプレートでキーワードが見つかり、処理された Web ページで対応する値が見つかります。

はい、これは多くのコーディングであり、私の説明が示すよりも困難です。Java プログラマーは、タスクをコーディングできるようになるまで、この説明をより単純なタスクに分解する必要があります。

于 2013-03-04T19:42:06.553 に答える
1

Web ページが頻繁に変更される場合は、MOVIE_RATING などのフィールドの検索をページの可能な限り小さな部分に限定し、それ以外はすべて無視することをお勧めします。2 つの可能性があります。各フィールドに正規表現を使用するか、ある種の CSS セレクターを使用することができます。どちらでも機能し、どちらの「テンプレート」も、適用する正規表現または css の検索式の単純なリストで構成できると思います。リストをスクロールして可能なものを抽出するだけで、ページが変更されたために特定のフィールドが見つからない場合は失敗します。

たとえば、正規表現は次のようになります。

"Score:"(.)*[0-9]\.[0-9]\/[0-9]

(私はこれをテストしていません。)

于 2013-03-07T00:09:27.937 に答える
1

私は、スペインの主要な不動産 Web サイトから RSS フィードを生成する私の個人的なプロジェクトで同様のことを行うために、次のアプローチを使用しました。

このツールを使用して、現在住んでいる賃貸物件を見つけました ;-)

  1. ページから HTML コードを取得する
  2. HTML を XHTML に変換します。私はこのライブラリを使用しました。今日、より良いオプションが利用可能であると思います
  3. XPath を使用して、関心のある情報に XHTML をナビゲートする

もちろん、元のページが変更されるたびに、XPath 式を変更する必要があります。私が考えることができるもう 1 つのアプローチ - 元の HTML ソースの意味論的分析 - は、私の謙虚なスキルをはるかに超えています ;-)

于 2013-03-12T12:53:20.820 に答える