КСМЛ рашчлањивање у Питхон-у
Овај чланак се фокусира на то како се може рашчланити дата КСМЛ датотека и издвојити неке корисне податке из ње на структуриран начин. КСМЛ: КСМЛ је скраћеница од еКстенсибле Маркуп Лангуаге. Дизајниран је за складиштење и транспорт података. Дизајниран је да буде читљив и људима и машинама. Зато циљеви дизајна КСМЛ-а наглашавају једноставност, општост и употребљивост широм Интернета. КСМЛ датотека која ће бити рашчлањена у овом водичу је заправо РСС феед. РСС: РСС (Рицх Сите Суммари који се често назива Реалли Симпле Синдицатион) користи породицу стандардних формата веб фидова за објављивање информација које се често ажурирају као што су уноси у блог, наслови вести, аудио видео. РСС је обичан текст у КСМЛ формату.
- Сам РСС формат је релативно лак за читање и аутоматизованим процесима и људима.
- РСС обрађен у овом туторијалу је РСС феед најбољих вести са популарне веб странице вести. Можете то проверити овде . Наш циљ је да обрадимо овај РСС феед (или КСМЛ фајл) и сачувамо га у неком другом формату за будућу употребу.
#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: - Учитајте РСС феед са наведеног УРЛ-а и сачувајте га као КСМЛ датотеку.
- Парсирајте КСМЛ датотеку да бисте вести сачували као листу речника где је сваки речник једна вест.
- Сачувајте вести у ЦСВ датотеку.
- Можете погледати више рсс фидова веб локације вести која се користи у горњем примеру. Можете покушати да направите проширену верзију горњег примера тако што ћете анализирати и друге рсс феедове.
- Да ли сте љубитељ крикета? Онда ово рсс феед мора да вас занима! Можете рашчланити ову КСМЛ датотеку да бисте извукли информације о утакмицама крикета уживо и да их користите да направите нотифиер за десктоп!
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 топневсфеед.кмл у нашем локалном именику. За више увида у то како функционише модул захтева, пратите овај чланак: ГЕТ и ПОСТ захтеви користећи Питхон
Овде користимо кмл.етрее.ЕлементТрее (кратко га назовите ЕТ) модул. Елемент Трее има две класе за ову сврху - ЕлементТрее представља цео КСМЛ документ као стабло и Елемент представља један чвор у овом стаблу. Интеракције са целим документом (читање и писање у/из датотека) се обично обављају на ЕлементТрее ниво. Интеракције са једним КСМЛ елементом и његовим поделементима се врше на Елемент ниво. Ок, идемо кроз парсеКСМЛ() function now: tree = ET.parse(xmlfile)Here we create an ЕлементТрее објекат рашчлањивањем прослеђеног кмфиле.
root = tree.getroot()гетроотед() функција враћа корен од дрво као ан Елемент 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 предмет елемент. ./цханнел/итем је заправо КСПатх синтаксу (КСПатх је језик за адресирање делова КСМЛ документа). Овде желимо да пронађемо све предмет унуци од канал деца оф тхе корен (означен са '.') елемент. Можете прочитати више о подржаној КСПатх синтакси овде . 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 предмет елементи где сваки предмет елемент садржи једну вест. Тако стварамо празно вести 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:
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'] дете.аттрибут је речник свих атрибута који се односе на елемент. Овде нас занима урл атрибут на медији: садржај namespace tag. Now for all other children we simply do: news[child.tag] = child.text.encode('utf8') дете.ознака садржи име подређеног елемента. дете.текст 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 невситемс . Коначно се ова листа враћа.
Као што видите, хијерархијски подаци КСМЛ датотеке су конвертовани у једноставну ЦСВ датотеку тако да се све вести чувају у облику табеле. Ово такође олакшава проширење базе података. Такође можете користити податке сличне ЈСОН-у директно у њиховим апликацијама! Ово је најбоља алтернатива за издвајање података са веб локација које не пружају јавни АПИ, али пружају неке РСС феедове. Сав код и датотеке коришћене у горњем чланку се могу пронаћи овде . Шта даље?