Reputation: 727
I using ElementTree to try and extract a number of values from an XML.
Here is a sample of the xml:-
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE playerstats>
<playerstats>
<steamID>76561197960964581</steamID>
<gameName>Team Fortress 2</gameName>
<stats>
<stat>
<name>Scout.accum.iNumberOfKills</name>
<value>1777</value>
</stat>
<stat>
<name>Scout.accum.iPlayTime</name>
<value>247469</value>
</stat>
<stat>
<name>Scout.accum.iPointCaptures</name>
<value>641</value>
</stat>
<stat>
<name>Soldier.accum.iNumberOfKills</name>
<value>1270</value>
</stat>
<stat>
<name>Soldier.accum.iPlayTime</name>
<value>94649</value>
</stat>
<stat>
<name>Spy.accum.iNumberOfKills</name>
<value>7489</value>
</stat>
<stat>
<name>Spy.accum.iPlayTime</name>
<value>1110582</value>
</stat>
</stats>
</playerstats>
There is a lot more, but this is just a sample.
I want to extract and sum all the values relating to "*.accum.iPlayTime", to calculate a total play time. Star implying all classes (e.g. scout, soldier, etc).
My code so far (including some of my attempts):-
playerStatsKISA = urllib2.urlopen('http://api.steampowered.com/ISteamUserStats/GetUserStatsForGame/v0002/?appid=440&key=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx&steamid=xxxxxxxxxxxxxxxxx&format=xml')
statsTF2 = playerStatsTF2.read()
theStatsTF2 = ET.fromstring(statsTF2)
totalTimesTF2 = theStatsKISA.findtext("Scout.accum.iPlayTime") # Didn't find anything
print totalTimesKISA
totalTimesTF2 = theStatsKISA.findall("./stats/stat/name")
for indiv in totalTimesTF2: # Another failed attempt
print indiv.attrib # didn't extract anything, I gather because the text I'm after is not an attribute but a value?
if indiv.attrib == 'Scout.accum.iPlayTime':
print "got it" # would extract value here, but it would be long winded to do this then try and extract the next value I'm actually after.
I was going with the idea of acquiring the value from each class then summing it. Though I gather there is probably a away to get all the value in one foul swoop using a * for the TF2 class name, but I was going to do that after I first worked out how to get the value from the tag following one that contained the value I needed.
Hope this made sense.
Thanks.
Upvotes: 0
Views: 2434
Reputation: 369454
Use text
attribute:
root = ET.fromstring(statsTF2)
for stat in root.findall("./stats/stat"):
if stat.find('name').text.endswith('.accum.iPlayTime'):
print stat.find('value').text
prints (given the xml in the question):
247469
94649
1110582
Using lxml
with XPath:
import lxml.etree as ET
root = ET.fromstring(statsTF2)
for text in root.xpath('./stats/stat[name[contains(text(), ".accum.iPlayTime")]]/value/text()'):
print text
Upvotes: 3
Reputation: 5336
This should work
totalTime = 0
root = ET.fromstring(statsTF2)
for stat in root.findall("./stats/stat"):
if stat.find('name').text.endswith('accum.iPlayTime'):
totalTime+=int(stat.find('value').text)
totalTime
>>> 1452700
Upvotes: 2