Razčlenjevanje XML v Pythonu

Razčlenjevanje XML v Pythonu
Ta članek se osredotoča na to, kako lahko razčlenimo dano datoteko XML in iz nje na strukturiran način izvlečemo nekaj uporabnih podatkov. XML: XML je kratica za eXtensible Markup Language. Zasnovan je bil za shranjevanje in prenos podatkov. Zasnovan je bil tako, da je berljiv za ljudi in stroje. Zato cilji oblikovanja XML poudarjajo preprostost, splošnost in uporabnost v internetu. Datoteka XML, ki bo razčlenjena v tej vadnici, je pravzaprav vir RSS. RSS: RSS (Rich Site Summary, ki se pogosto imenuje Really Simple Syndication) uporablja družino standardnih formatov spletnih virov za objavo pogosto posodobljenih informacij, kot so zapisi v spletnem dnevniku, naslovi novic, avdio video. RSS je golo besedilo v formatu XML.
  • Sam format RSS je razmeroma enostaven za branje tako z avtomatiziranimi procesi kot tudi s strani ljudi.
  • RSS, obdelan v tej vadnici, je vir RSS najpomembnejših novic s priljubljenega spletnega mesta z novicami. Lahko preverite tukaj . Naš cilj je obdelati ta vir RSS (ali datoteko XML) in ga shraniti v drugi obliki za prihodnjo uporabo.
Uporabljen modul Python: Ta članek se bo osredotočil na uporabo vgrajenih xml modul v pythonu za razčlenjevanje XML, glavni poudarek pa bo na ElementTree XML API tega modula. Izvedba: Python
   #Python code to illustrate parsing of XML files   # importing the required modules   import   csv   import   requests   import   xml.etree.ElementTree   as   ET   def   loadRSS  ():   # url of rss feed   url   =   'http://www.hindustantimes.com/rss/topnews/rssfeed.xml'   # creating HTTP response object from given url   resp   =   requests  .  get  (  url  )   # saving the xml file   with   open  (  'topnewsfeed.xml'     'wb'  )   as   f  :   f  .  write  (  resp  .  content  )   def   parseXML  (  xmlfile  ):   # create element tree object   tree   =   ET  .  parse  (  xmlfile  )   # get root element   root   =   tree  .  getroot  ()   # create empty list for news items   newsitems   =   []   # iterate news items   for   item   in   root  .  findall  (  './channel/item'  ):   # empty news dictionary   news   =   {}   # iterate child elements of item   for   child   in   item  :   # special checking for namespace object content:media   if   child  .  tag   ==   '{https://video.search.yahoo.com/mrss'  :   news  [  'media'  ]   =   child  .  attrib  [  'url'  ]   else  :   news  [  child  .  tag  ]   =   child  .  text  .  encode  (  'utf8'  )   # append news dictionary to news items list   newsitems  .  append  (  news  )   # return news items list   return   newsitems   def   savetoCSV  (  newsitems     filename  ):   # specifying the fields for csv file   fields   =   [  'guid'     'title'     'pubDate'     'description'     'link'     'media'  ]   # writing to csv file   with   open  (  filename     'w'  )   as   csvfile  :   # creating a csv dict writer object   writer   =   csv  .  DictWriter  (  csvfile     fieldnames   =   fields  )   # writing headers (field names)   writer  .  writeheader  ()   # writing data rows   writer  .  writerows  (  newsitems  )   def   main  ():   # load rss from web to update existing xml file   loadRSS  ()   # parse xml file   newsitems   =   parseXML  (  'topnewsfeed.xml'  )   # store news items in a csv file   savetoCSV  (  newsitems     'topnews.csv'  )   if   __name__   ==   '__main__'  :   # calling main function   main  ()   
Above code will:
  • Naloži vir RSS z navedenega URL-ja in ga shrani kot datoteko XML.
  • Razčlenite datoteko XML, da shranite novice kot seznam slovarjev, kjer je vsak slovar ena sama novica.
  • Shranite novice v datoteko CSV.
Poskusimo razumeti kodo po delih:
    Nalaganje in shranjevanje vira RSS
    def loadRSS(): # url of rss feed url = 'http://www.hindustantimes.com/rss/topnews/rssfeed.xml' # creating HTTP response object from given url resp = requests.get(url) # saving the xml file with open('topnewsfeed.xml' 'wb') as f: f.write(resp.content) 
    Here we first created a HTTP response object by sending an HTTP request to the URL of the RSS feed. The content of response now contains the XML file data which we save as topnewsfeed.xml v našem lokalnem imeniku. Za več informacij o delovanju modula za zahteve sledite temu članku: Zahteve GET in POST z uporabo Pythona Razčlenjevanje XML Ustvarili smo razčleniXML() funkcijo za razčlenitev datoteke XML. Vemo, da je XML sam po sebi hierarhični format podatkov in da je najbolj naraven način za predstavitev z drevesom. Oglejte si na primer spodnjo sliko: razčlenjevanje XML Tukaj uporabljamo xml.etree.ElementTree (na kratko ga imenujemo ET) modul. Drevo elementov ima za ta namen dva razreda - ElementTree predstavlja celoten dokument XML kot drevo in Element predstavlja eno vozlišče v tem drevesu. Interakcije s celotnim dokumentom (branje in pisanje v/iz datotek) se običajno izvajajo na ElementTree raven. Interakcije z enim samim elementom XML in njegovimi podelementi se izvajajo na Element raven. V redu, pojdimo skozi razčleniXML() function now:
    tree = ET.parse(xmlfile) 
    Here we create an ElementTree objekt z razčlenjevanjem podanega xmlfile.
    root = tree.getroot() 
    getrooted() funkcija vrne koren drevo kot Element object.
    for item in root.findall('./channel/item'): 
    Now once you have taken a look at the structure of your XML file you will notice that we are interested only in postavka element. ./kanal/postavka je dejansko XPath sintakso (XPath je jezik za naslavljanje delov dokumenta XML). Tukaj želimo najti vse postavka vnuki kanal otroci iz korenina (označen z '.'). Preberete lahko več o podprti sintaksi XPath tukaj .
    for item in root.findall('./channel/item'): # empty news dictionary news = {} # iterate child elements of item for child in item: # special checking for namespace object content:media if child.tag == '{https://video.search.yahoo.com/mrss': news['media'] = child.attrib['url'] else: news[child.tag] = child.text.encode('utf8') # append news dictionary to news items list newsitems.append(news) 
    Now we know that we are iterating through postavka elementov, kjer vsak postavka element vsebuje eno novico. Tako ustvarimo prazno novice dictionary in which we will store all data available about news item. To iterate though each child element of an element we simply iterate through it like this:
    for child in item: 
    Now notice a sample item element here: Razčlenjevanje XML v Pythonu We will have to handle namespace tags separately as they get expanded to their original value when parsed. So we do something like this:
    if child.tag == '{https://video.search.yahoo.com/mrss': news['media'] = child.attrib['url'] 
    otrok.attrib je slovar vseh atributov, povezanih z elementom. Tukaj nas zanima url atribut od mediji: vsebina namespace tag. Now for all other children we simply do:
    news[child.tag] = child.text.encode('utf8') 
    otrok.oznaka vsebuje ime podrejenega elementa. otrok.besedilo stores all the text inside that child element. So finally a sample item element is converted to a dictionary and looks like this:
    {'description': 'Ignis has a tough competition already from Hyun....  'guid': 'http://www.hindustantimes.com/autos/maruti-ignis-launch....  'link': 'http://www.hindustantimes.com/autos/maruti-ignis-launch....  'media': 'http://www.hindustantimes.com/rf/image_size_630x354/HT/...  'pubDate': 'Thu 12 Jan 2017 12:33:04 GMT ' 'title': 'Maruti Ignis launches on Jan 13: Five cars that threa..... } 
    Then we simply append this dict element to the list novice . Končno je ta seznam vrnjen. Shranjevanje podatkov v datoteko CSV Sedaj preprosto shranimo seznam novic v datoteko CSV, tako da ga lahko v prihodnje enostavno uporabimo ali spremenimo z savetoCSV() funkcijo. Če želite izvedeti več o pisanju elementov slovarja v datoteko CSV, preberite ta članek: Delo z datotekami CSV v Pythonu
Tukaj je torej, kako so zdaj videti naši oblikovani podatki: rezultat Kot lahko vidite, so bili podatki hierarhične datoteke XML pretvorjeni v preprosto datoteko CSV, tako da so vse novice shranjene v obliki tabele. To olajša tudi razširitev baze podatkov. Podatke, podobne JSON, lahko uporabite tudi neposredno v svojih aplikacijah! To je najboljša alternativa za pridobivanje podatkov s spletnih mest, ki ne ponujajo javnega API-ja, vendar ponujajo nekaj virov RSS. Najdete lahko vso kodo in datoteke, uporabljene v zgornjem članku tukaj . Kaj pa potem?
  • Ogledate si lahko več virov rss spletnega mesta z novicami, uporabljenega v zgornjem primeru. Lahko poskusite ustvariti razširjeno različico zgornjega primera tako, da razčlenite tudi druge vire rss.
  • Ste ljubitelj kriketa? Potem to rss vir vas mora zanimati! To datoteko XML lahko razčlenite, da postrgate informacije o tekmah kriketa v živo in jih uporabite za izdelavo namiznega obvestila!
Kviz HTML in XML Ustvari kviz