Ruby VIII.
Tentokrát se podíváme, jak zpracovat soubory XML pomocí jazyka Ruby
28.4.2012 21:00 |
Jakub Lares
| Články autora
| přečteno 1327×
Základy práce s XML
XML nemá předem daná pravidla pro reprezentaci datových struktur - tyto struktury musíme sami navrhnout a implementovat. Výhodou je o něco větší flexibilita tohoto datového formátu a možnost nadefinovat si skutečně libovolné struktury přesně odpovídající datové doméně. Pomocí knihovny REXML nejdříve vytvoříme XML dokument s kořenovým elementem data, ve kterém jsou jednotlivé položky pole uložené ve vnořených elementech animal. Toto XML zapíšeme do řetězce, který potom následně opět pomocí knihovny REXML načteme, a převedeme zpět na původní pole. Zde, nalezneme soubory, se kterými budeme dneska pracovat.
require 'rexml/document'
data = ['Cat', 'Dog', 'Elepahnt']
puts 'Input data:'
p data
doc = REXML::Document.new
doc << REXML::XMLDecl.new
root = REXML::Element.new('data')
data.each do |value|
new_element = REXML::Element.new('animal')
new_element.text = value
root.elements << new_element
end
doc.elements << root
xml = ""
doc.write(xml,2,false)
puts "Converted to XML"
puts xml
data2 = []
doc2 = REXML::Document.new(xml)
doc2.root.elements.each do |element|
data2 << element.text.strip
end
puts "Parsed from XML:"
p data2
Výstup
Input data:
["Cat", "Dog", "Elepahnt"]
Converted to XML
<?xml version='1.0'?>
<data>
<animal>
Cat
</animal>
<animal>
Dog
</animal>
<animal>
Elepahnt
</animal>
</data>
Parsed from XML:
["Cat", "Dog", "Elepahnt"]
Vytvoření XML pomocí knihovny REXML
V tomto příkladu zkusíme do XML zapsat datovou strukturu ze souboru quiz_object.yaml. Načtení této datové struktury do objektů provedeme metodou YAML.load_file. Aby toto načtení fungovalo, tak musíme mít přístupné definice příslušných tříd - o toto se stará příkaz require. REXML API pro vytváření XML je poměrně jednoduché, je to kombinace vytváření nových elementů pomocí Element.new, nastavování atributů elementům pomocí přístupové metody attributes, a vkládání podřazených elementů operátorem << do pole elements. Výsledné XML se uloží do souboru voláním doc.write.
require 'rexml/document'
require 'yaml'
require 'quiz_classes'
source_file = 'quiz_object.yaml'
target_file = 'quiz_object_rexml.xml'
quiz_object = YAML.load_file(source_file)
puts "Quiz data loaded from #{source_file}"
doc = REXML::Document.new
doc << REXML::XMLDecl.new
root = REXML::Element.new('quiz')
root.attributes['name'] = quiz_object.name
root.attributes['author'] = quiz_object.author
quiz_object.questions.each do |question|
new_question = REXML::Element.new('question')
new_question.attributes['text'] = question.text
question.answers.each do |answer|
new_answer = REXML::Element.new('answer')
new_answer.text = answer.text
correct = "0"
correct = "1" if answer.correct
new_answer.attributes['correct'] = correct
new_question.elements << new_answer
end
root.elements << new_question
end
doc.elements << root
File.open("quiz_object_rexml.xml","w") do |file|
doc.write(file,2)
end
puts "Quiz data written to #{target_file}"
puts
File.open(target_file,"r") do |file|
file.each_line do |line|
puts line
end
end
Výstup
Quiz data loaded from quiz_object.yaml
Quiz data written to quiz_rexml.xml
<?xml version='1.0'?>
<quiz name='Test vseobecnych znalosti' author='Tomas Marny'>
<question text='Hlavni mesto San Marina?'>
<answer correct='0'>
Torino
</answer>
<answer correct='1'>
San Marino
</answer>
<answer correct='0'>
Vatikan
</answer>
<answer correct='0'>
Terst
</answer>
</question>
...
Vytvoření XML pomocí knihovny Builder
Stejné XML jako v předchozím příkladu můžeme o něco úsporněji vytvořit pomocí knihovny builder. Pokud tuto knihovnu nemáte, tak si ji nainstalujte v NetBeans v menu Tools > Ruby Gems > New Gems > Search: builder.
Knihovna builder nabízí oproti REXML o něco úspornější API, které využívá dynamických vlastností jazyka Ruby. XML vytváříme voláním metod na objektu Builder::XmlMarkup, kde jméno volané metody je přímo jménem vytvářeného elementu, a případný textový obsah a atributy elementu se předají jako parametry této metody. Pro odlišení speciální metody (jako např instruct! pro vložení XML hlavičky) končí vykřičníkem. XML se zapisuje přímo do souboru, který jsme předali objektu Builder::XmlMarkup v parametru target.
require 'rubygems'
require 'builder'
require 'yaml'
require 'quiz_classes'
source_file = 'quiz_object.yaml'
target_file = 'quiz_object_builder.xml'
quiz_object = YAML.load_file(source_file)
puts "Quiz data loaded from #{source_file}"
File.open(target_file,'w') do |file|
xml = Builder::XmlMarkup.new({:target => file, :indent => 2})
xml.instruct!
xml.quiz({'name' => quiz_object.name, 'author' => quiz_object.author}) do
quiz_object.questions.each do |question|
xml.question({'text' => question.text}) do
question.answers.each do |answer|
correct = 0
correct = 1 if answer.correct
xml.answer(answer.text, {'correct' => correct})
end
end
end
end
end
puts "Quiz data written to #{target_file}"
puts
File.open(target_file,"r") do |file|
file.each_line do |line|
puts line
end
end
Výstup
Quiz data loaded from quiz_object.yaml
Quiz data written to quiz_builder.xml
<?xml version="1.0" encoding="UTF-8"?>
<quiz name="Test vseobecnych znalosti" author="Tomas Marny">
<question text="Hlavni mesto San Marina?">
<answer correct="0">Torino</answer>
<answer correct="1">San Marino</answer>
<answer correct="0">Vatikan</answer>
<answer correct="0">Terst</answer>
</question>
...
Načítání XML pomocí stromového rozhraní
V tomto příkladu načítáme XML stejným způsobem jako v prvním příkladu, pouze se jedná trochu složitější soubor. Čteme právě to XML, které jsme vytvořili v minulém příkladu. Základem jsou dvě vnořené smyčky, z nichž jedna iteruje přes otázky (root.elements) a druhá přes odpovědi (question.elements). V průběhu iterace vytváříme výsledné objekty. Seznam otázek vypíšeme metodou print_quiz.
require 'rexml/document'
require 'yaml'
require 'quiz_classes'
source_file = 'quiz_builder.xml'
puts "Parsing source file #{source_file}"
File.open(source_file,"r") do |file|
doc = REXML::Document.new(file)
name = doc.root.attributes['name']
author = doc.root.attributes['author']
quiz = Quiz.new(name,author,Array.new)
doc.root.elements.each do |question|
new_question = Question.new(question.attributes['text'],Array.new)
question.elements.each_with_index do |answer,i|
correct = false
correct = true if answer.attributes['correct']=="1"
new_question.answers << Answer.new(answer.text.strip,correct)
end
quiz.questions << new_question
end
quiz.print_quiz
end
Výstup
Parsing source file quiz_builder.xml
Test vseobecnych znalosti
Tomas Marny
1. Hlavni mesto San Marina?
a) Torino
b) San Marino
c) Vatikan
d) Terst
Soubory ke stažení
RAR archív s příklady
Závěr
Toto je pro dnešek vše, příště si řekneme něco o unit testech a dokumentaci.
Verze pro tisk
| |
|
Nejsou žádné diskuzní příspěvky u dané položky.
Příspívat do diskuze mohou pouze registrovaní uživatelé.
|
|

Vyhledávání software

Vyhledávání článků
22.5.2013 6:46 /MaReK Olšavský Svobodný software ve státní sféře nejsou jen vítězství, ale i mýty a pověry, které jej vylučují z výběru. 5 nejčastějších hloupostí o F/L/OSS zkritizoval Adam Firestone na stránkách OpenSource.com. Nesetkáváme se s podobnými argumenty i při snaze prosadit svobodný software ve firmách a u soukromých osob?
Přidat komentář
22.5.2013 6:46 /MaReK Olšavský Embedovatelná databáze SQLite byla vydána ve verzi 3.7.17, která nabízí větší rychlost (v některých úlohách až dvojnásobnou), opravy několika chyb, nebo vylepšení možností nahrávání rozšíření. O SQLite se píše výrazně méně, než o konkurenci, ale velmi pravděpodobně jde o nejčastěji nasazené řešení, díky mnoha aplikacím.
Přidat komentář
22.5.2013 6:45 /MaReK Olšavský 14. května 2013 IBM oznámila konec vývoje Lotus SmartSuite , Lotus Organizer a Lotus 1-2-3, balíků aplikací, jež byly považovány za špičku v oboru. Krátký nekrolog za legendární Lotus 1-2-3, který byl vyvíjen 30 let, sepsal Steven J. Vaughan-Nichols.
Přidat komentář
21.5.2013 7:05 /MaReK Olšavský Vydání nástupce kdysi velmi populární distribuce GNU/Linuxu, Mandrake/Mandrivy, Mageia již nebude dále odkládáno, s 2 měsíčním zpožděním vyšla Mageia 3. Z novinek vybíráme: KDE 4.10.2, GNOME 3.6, LibreOffice 4.03, nebo Steam pro Linux. Mageia patří mezi distribuce, které lze doporučit méně zkuženým uživatelům.
Přidat komentář
21.5.2013 7:05 /MaReK Olšavský Chytré telefony s operačním systémem Sailfish OS (který vytváří společnost Jolla, jež vznikla z bývalých vývojářů Maema Nokie) se blíží uvedení na trh, předobjednávka s dodáním na konci roku 2013 a kompatibilita s Androidími aplikacemi ukazují na blízkost cíle. Rozhovor s Marcem Dillonem odhaluje mnohé z pozadí vývoje. Není bez zajímavosti, že první aplikace byla zveřejněna pouhých 29 minut po vydání SDK.
Přidat komentář
21.5.2013 7:05 /MaReK Olšavský Z koupě populární služby Tumblr firmou Yahoo za 1,1 mld. US$ nemalou měrou těží svobodný Wordpress, jemuž narostl počet importovaných blogů z Tumblr přibližně 150×.
Přidat komentář
21.5.2013 7:05 /MaReK Olšavský Ač se to mnohým může zdát neuvěřitelné, COBOL stále patří mezi živé jazyky. Firma IBM rozšířila jeho schopnosti o podporu XML a Javy 7, se současným nárůstem výkonu o 15—20 %.
Přidat komentář
20.5.2013 6:53 /MaReK Olšavský Vývojářský tým NetBSD vydal verzi 6.1 operačního systému, jenž je portován pro drtivou většinu používaných platforem. Jelikož se jedná o upgrade stávající řady, přináší nová verze převážně jen opravy. V duchu oprav vydání vyšla i verze 6.0.2.
Přidat komentář
Více ...
Přidat zprávičku
 Poslední diskuze
18.5.2013 17:55 /
Martin Kumst Re: zaheslování bash scriptu nebo složky
18.5.2013 7:44 /
--- Re: Prosím o pomoc či radu
15.5.2013 19:21 /
Filip Vaněček Cesty k souborům při používání coolurl
13.5.2013 6:50 /
Radim Kolář Zabbix
8.5.2013 6:07 /
MaReK Olšavský Web Upd8
Více ...
|