0

CSVデータベース/Ruby配列にスクレイプしようとしているページには、不均一なサイズのグループの合計470のレコードがリストされており、各グループの前に日付があります(合計22の一意の日付)。

グループはHTMLテーブルに編成されておらず、「親」が各グループの日付につながる可能性のあるDOMの階層も、<div class="line">表示されているレコードdivのドライリストのみであり、前にのみが表示されることもあるため、その方法がわかりません。<span class="date">Thursday, May 24, 2012</span>新しい日付が印刷されるまで、次のXレコードにのみ適用される日付を保持します。

そのirb中で正しく表示されます:

$page = $agent.get(pageurl) # gets page with Mechanize
doc = $page.parser # returns Nokogiri::HTML 

(records = doc.search('html body div#wrapper div#innerwrapper div#content div.line')).size 
=> 470
(dates = doc.search('html body div#wrapper div#innerwrapper div#content span.date')).size 
=> 22

たとえば、最初の日付を表示します。

doc.search('html body div#wrapper div#innerwrapper div#content span.date')[0].text
=> "Wednesday, May 23, 2012"

私の目標は、CSVファイルに保存する前に、上記の470レコードのdoc.searchのそれぞれにフィールドとして正しい日付を追加することです。

Nokogiri(またはMechanize)は、DOM内の位置に基づいて、つまり次の直後でdates[N].textあるが次の前に、グループでこれらのレコードを取得するのに役立ちます<span class="date">か?

Nを0から21まで繰り返して、470レコードすべてのマスター配列/ CSVオブジェクトに追加できますが、グループごとに適切なdateフィールドを追加します。

4

2 に答える 2

1

まず、検索を少し簡略化できます。コンテンツはでありid、定義上、その特定divのを一意に識別するため、前述のパス情報は必要ありません。

records = doc.search('div#content div.line')

各レコードから、xpathのpreceding-sibling軸を使用して日付を取得できます。全体として:

doc.search('div#content div.line').each do |record|
  date = record.xpath('preceding-sibling::span[@class="date"][1]').text
  #append to CSV
end

preceding-sibling::spanXPathによると: 「日付」()のクラスを持つ同じレベル()で先行するスパンを見つけ、[@class="date"]最初のそのようなスパン([1])を取得して、最も近い日付スパンを取得するようにします)。

于 2012-05-22T11:51:01.207 に答える
1

これは、トラバースを使用するもう1つの良い時期です。

doc.traverse do |node|
  @date = node.text if 'span' == node.name && 'date' == node[:class]
  puts [@date, node.text].join(', ') if 'div' == node.name && 'line' == node[:class]
end
于 2012-05-22T14:13:11.287 に答える