Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
220 changes: 207 additions & 13 deletions dataranges.py
100755 → 100644
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,13 @@
'''Data range checker for Naev.

Run this script from the root directory of your Naev source tree. It
reads the XML files in dat/ssys/ and gives details of the ranges of
values for certain key statistics. Example usage:
reads the XML files in dat/ssys/ and dat/assets/ and gives details of
the ranges of values for certain statistics. Example usage:
user@home:~/naev/$ dataranges

'''

# Copyright © 2012 Tim Pederick.
# Copyright © 2012 Tim Pederick, 2013 Johann Bryant.
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
Expand All @@ -18,18 +18,18 @@
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
# along with this program. If not, see <http://www.gnu.org/licenses/>.

# Standard library imports.
import math

# Local imports.
from dataloader import datafiles
from naevdata import SSystem
from naevdata import SSystem, Asset

def stats(iterable):
'''Find the mean and standard deviation of a data set.'''
Expand All @@ -48,6 +48,12 @@ def liststr(items):
return (', '.join(str(item) for item in items[:-1]) +
' and ' + str(items[-1]))

def hypot(x, y):
'''Find the straightline distance of an asset in space.'''
length = math.sqrt((x*x)+(y*y))

return length

def main():
ssystems = []
for ssysfile in datafiles('SSystems'):
Expand All @@ -64,6 +70,14 @@ def main():
most_stars_at, most_stars, stars = [], 0, []
least_stars_at, least_stars = [], float('Inf')

most_jumps_at, most_jumps, jumps = [], 0, []
least_jumps_at, least_jumps = [], float('Inf')
zero_jumps_at = []

most_planets_at, most_planets, planets = [], 0, []
least_planets_at, least_planets = [], float('Inf')
zero_planets_at = []

for ssys in ssystems:
neb_densities.append(ssys.nebula.density)
if ssys.nebula.density > neb_density:
Expand Down Expand Up @@ -110,19 +124,57 @@ def main():
least_stars_at.append(ssys.name)
# ...else this isn't a candidate for the least starry system.

jump_num = len(ssys.jumps)
jumps.append(jump_num)
if jump_num > most_jumps:
most_jumps_at, most_jumps = [ssys.name], jump_num
elif jump_num == most_jumps:
most_jumps_at.append(ssys.name)
# ...else this isn't a candidate for the system with the most jumps.
if jump_num == 0:
zero_jumps_at.append(ssys.name)
# ...else this isn't a system with zero jumps.
else:
if jump_num < least_jumps:
least_jumps_at, least_jumps = [ssys.name], jump_num
elif jump_num == least_jumps:
least_jumps_at.append(ssys.name)
# ...else this isn't a candidate for the system with the least jumps.

planet_num = 0
for asset in ssys.assets:
if not (asset.find('Virtual') + 1):
planet_num = planet_num + 1
# ...else this asset is Virtual.
planets.append(planet_num)
if planet_num > most_planets:
most_planets_at, most_planets = [ssys.name], planet_num
elif planet_num == most_planets:
most_planets_at.append(ssys.name)
# ...else this isn't a candidate for the system with the most planets.
if planet_num == 0:
zero_planets_at.append(ssys.name)
# ...else this isn't a system with zero planets.
else:
if planet_num < least_planets:
least_planets_at, least_planets = [ssys.name], planet_num
elif planet_num == least_planets:
least_planets_at.append(ssys.name)
# ...else this isn't a candidate for the system with the least planets.

print('Radius: μ={}, σ={}'.format(*stats(radii)))
print('The largest system radius',
'({}) is found in {}.'.format(hi_radius, liststr(largest_system)))
'({}) can be found in {}.'.format(hi_radius, liststr(largest_system)))
print('The smallest system radius',
'({}) is found in {}.'.format(lo_radius, liststr(smallest_system)))
'({}) can be found in {}.'.format(lo_radius, liststr(smallest_system)))
print()
print('Nebula density: μ={}, σ={}'.format(*stats(neb_densities)))
print('The densest nebula ({}) is in {}.'.format(neb_density,
liststr(neb_densest_at)))
print('The densest part of the nebula',
'({}) can be found in {}.'.format(neb_density, liststr(neb_densest_at)))
print()
print('Nebula volatility: μ={}, σ={}'.format(*stats(neb_volatilities)))
print('The nebula is at its most volatile',
'({}) in {}.'.format(neb_volatility, liststr(neb_worst_at)))
print('The most volatile part of the nebula',
'({}) can be found in {}.'.format(neb_volatility, liststr(neb_worst_at)))
print()
print('Interference: μ={}, σ={}'.format(*stats(interferences)))
print('Interference is at its peak',
Expand All @@ -133,6 +185,148 @@ def main():
'({}) are found in {}.'.format(most_stars, liststr(most_stars_at)))
print('The least starry skies',
'({}) are found in {}.'.format(least_stars, liststr(least_stars_at)))
print()
print('Jumps: μ={}, σ={}'.format(*stats(jumps)))
print('The most jump points',
'({}) are found in {}.'.format(most_jumps, liststr(most_jumps_at)))
print('The least jump points',
'({}) are found in {}.'.format(least_jumps, liststr(least_jumps_at)))
print('There are zero jump points in {}.'.format(liststr(zero_jumps_at)))
print()
print('Planets: μ={}, σ={}'.format(*stats(planets)))
print('The most planets',
'({}) can be found in {}.'.format(most_planets, liststr(most_planets_at)))
print('The least planets',
'({}) can be found in {}.'.format(least_planets, liststr(least_planets_at)))
print('There are zero planets in {} systems.'.format(len(zero_planets_at)))
print()

assets = []
for assetsfile in datafiles('Assets'):
# Parse each XML file into a Asset object.
assets.append(Asset(assetsfile))

furthest, hi_orbit, orbits = [], 0.0, []
nearest, lo_orbit = [], float('Inf')

best_hidden, hi_hide, hides = [], 0.0, []
worst_hidden, lo_hide = [], float('Inf')

most_pop, hi_pop, pops = [], 0.0, []
least_pop, lo_pop, total_pops = [], float('Inf'), []

world_classes, class_matches = dict(), dict()

for asset in assets:
if not asset.virtual:
orbit = hypot(asset.pos.x, asset.pos.y)
orbits.append(orbit)
if orbit > hi_orbit:
furthest, hi_orbit = [asset.name], orbit
elif orbit == hi_orbit:
furthest.append(asset.name)
# ...else this isn't a candidate for the biggest orbit.
if orbit < lo_orbit:
nearest, lo_orbit = [asset.name], orbit
elif orbit == lo_orbit:
nearest.append(asset.name)
# ...else this isn't a candidate for the smallest orbit.

hides.append(asset.hide)
if asset.hide > hi_hide:
best_hidden, hi_hide = [asset.name], asset.hide
elif asset.hide == hi_hide:
best_hidden.append(asset.name)
# ...else this isn't a candidate for the best hidden.
if asset.hide < lo_hide:
worst_hidden, lo_hide = [asset.name], asset.hide
elif asset.hide == lo_hide:
worst_hidden.append(asset.name)
# ...else this isn't a candidate for the least hidden.

if asset.world_class in world_classes:
world_classes[asset.world_class] += 1
else:
world_classes.update({asset.world_class: 1,})
if asset.world_class.isalpha:
if asset.gfx['space'][0] == asset.world_class:
if asset.world_class in class_matches:
class_matches[asset.world_class] += 1
else:
class_matches.update({asset.world_class: 1,})
elif asset.gfx['space'][5] == asset.world_class:
if asset.world_class in class_matches:
class_matches[asset.world_class] += 1
else:
class_matches.update({asset.world_class: 1,})
elif asset.gfx['space'][0] == 'a':
if asset.gfx['space'][9] == asset.world_class:
if asset.world_class in class_matches:
class_matches[asset.world_class] += 1
else:
class_matches.update({asset.world_class: 1,})
# ...else world class doesn't match the planet, moon or asteroid space graphic

total_pops.append(asset.population)
if asset.population > 0:
pops.append(asset.population)
if asset.population > hi_pop:
most_pop, hi_pop = [asset.name], asset.population
elif asset.population == hi_pop:
most_pop.append(asset.name)
# ...else this isn't a candidate for the biggest population.
if asset.population < lo_pop:
least_pop, lo_pop = [asset.name], asset.population
elif asset.population == lo_pop:
least_pop.append(asset.name)
# ...else this isn't a candidate for the smallest population.

print('Orbit: μ={}, σ={}'.format(*stats(orbits)))
print('The biggest orbit',
'({}) can be found in {}.'.format(hi_orbit, liststr(furthest)))
print('The smallest orbit',
'({}) can be found in {}.'.format(lo_orbit, liststr(nearest)))
print()
print('Difficulty in sensing: μ={}, σ={}'.format(*stats(hides)))
print('The asset(s) most difficult to find',
'({}) is or are {}.'.format(hi_hide, liststr(best_hidden)))
print('The asset(s) least difficult to find',
'({}) is or are {}.'.format(lo_hide, liststr(worst_hidden)))
print()
print('Population (everywhere): μ={}, σ={}'.format(*stats(total_pops)))
print('Population (inhabitted planets only): μ={}, σ={}'.format(*stats(pops)))
print('The biggest population',
'({}) can be found on {}.'.format(hi_pop, liststr(most_pop)))
print('The smallest (greater than zero) population',
'({}) can be found on {}.'.format(lo_pop, liststr(least_pop)))
print()
for world_class in sorted(world_classes.keys()):
asset_type = 'unknown'
station_type = 'unknown'
extra_data = ''

if world_class in ['0', '1', '2', '3']:
# would prefer to pull the following data from naev/src/space.h
asset_type = 'station'
if world_class == '0': station_type = 'civilian'
elif world_class == '1': station_type = 'military'
elif world_class == '2': station_type = 'interfactional'
elif world_class == '3': station_type = 'robotic'
extra_data = ' (' + station_type + ')'
elif world_class in class_matches:
asset_type = 'planet'
extra_data = ' (' + repr(math.ceil((world_classes[world_class] - class_matches[world_class]) / world_classes[world_class] * 100)) + '% don\'t match their space GFX)'
else:
asset_type = 'planet'
extra_data = ' (100% don\'t match their space GFX)'

if world_classes[world_class] == 1:
print('There is 1 class {} {}{}.'
.format(world_class, asset_type, extra_data))
else:
print('There are {} class {} {}s{}.'
.format(world_classes[world_class], world_class, asset_type, extra_data))
print()

if __name__ == '__main__':
main()
main()