1

データをフェッチする必要のあるXMLタグを含む最大1GBのXMLファイルがあります。次の形式のXMLファイルがあります(実際のファイルのサイズは約ギガバイトであるため、サンプルデータのみを貼り付けています)。

report.xml

<report>
  <report-name name="ALL_TIME_KEYWORDS_PERFORMANCE_REPORT"/>
  <date-range date="All Time"/>
  <table>
  <row campaignID="79057390" adGroupID="3451305670" keywordID="3000000" keyword="Content" avgPosition="1.55" cost="252910000" clicks="11" conv1PerClick="0" impressions="7395" day="2012-04-23" currency="INR" account="Virtual Voyage" timeZone="(GMT+05:30) India Standard Time" viewThroughConv="0"/>

  <row campaignID="79057390" adGroupID="3451305670" keywordID="3000000" keyword="Content" avgPosition="1.16" cost="0" clicks="0" conv1PerClick="0" impressions="160" day="2012-04-23" currency="INR" account="Virtual Voyage" timeZone="(GMT+05:30) India Standard Time" viewThroughConv="0"/>

  <row campaignID="79057390" adGroupID="3451305670" keywordID="3000000" keyword="Content" avgPosition="1.56" cost="0" clicks="0" conv1PerClick="0" impressions="34" day="2012-04-23" currency="INR" account="Virtual Voyage" timeZone="(GMT+05:30) India Standard Time" viewThroughConv="0"/>

  </table>
</report>
  1. XMLファイルを解析/処理し、Pythonでxmlタグからデータをフェッチするための最良の方法は何ですか?

  2. XMLファイルを処理できるフレームワークはありますか?

  3. メソッドは高速である必要があります。100秒以内に終了する必要があります。

私はPythonでHadoopを使用してXMLファイルを処理してきましたが、通常、データを処理するだけで200秒近くかかります...したがって、上記のXMLタグを解析し、タグからデータをフェッチする代替ソリューションを探しています。

ある意味でのタグからのデータは次のとおりです。

 campaignID="79057390" adGroupID="3451305670" keywordID="3000000" keyword="Content" avgPosition="1.16" cost="0" clicks="0" ...

XMLファイルを処理した後、データと値(79057390,3451305670 ...)をMySQLデータベースに保存します。必要なのは、サイズが約1GBのXMLファイルを処理し、処理されたデータを100秒未満でMySQLデータベースに保存できるようにすることだけです。

4

1 に答える 1

2

私は最近同様の問題に直面しました。それを解決する方法は、iterparse関数とlxmlを使用することでした。最後に、これはすべてDOMのようなパーサーではなくSAXのようなパーサーを使用することに基づいています。DOMはメモリ内で機能することを忘れないでください。 SAXはイベント駆動型であるため、SAXを使用して大量のメモリを節約できます(解析するためにすべてのドキュメントをロードするのを待つ必要がないため、時間もかかります!)

このようなものが使えると思います

import xml.etree.cElementTree as ET

file_path = "/path/to/your/test.xml"
context = ET.iterparse(file_path, events=("start", "end")) #Probably we could use only the start tag
# turn it into an iterator
context = iter(context)
on_members_tag = False

for event, elem in context:
    tag = elem.tag
    value = elem.text
    if value :
        value = value.encode('utf-8').strip()       
    if event == 'start' :
        if tag == "row" :
            attribs = elem.attrib
            print "This is the campaignID %s and this is the adGroupID" % (attribs['campaignID'] , attribs['adGroupID'])

    elem.clear() #Save memory!
于 2012-11-30T06:35:09.157 に答える