idf

#OSM parser, python et ImageDraw, j’ai codé comme un sagouin !

OSM Parser, j'ai codé comme un sagouin... et c'est pas gentil pour les sagouins

  Dans un article précédant, je me contentais de charger en mémoire les données OpenStreetMap de l'Ile de France sans rien en faire. J'ai ajouté quelques lignes pour faire un point blanc sur une image pour charge node que je charge du fichier OSM. Le résultat est plutôt pas mal !
alsace

Je ne sais pas si vous l'avez reconnue, mais c'est l’Alsace .. et en image de l'article c'est l'Ile de France.

Voila le bout de code:
/usr/bin/python
from imposm.parser import OSMParser
import collections
import pprint
import os
import psutil
import Image, ImageDraw

class DataHandler(object):
    w = {}
    n = {}
    #collections.OrderedDict()    
    def ways(self, ways):
        # callback method for ways
        for osmid, tags, refs in ways:
                self.w[osmid] = {}
                self.w[osmid]['tags'] = tags
                self.w[osmid]['refs'] = refs
    def nodes(self, nodes):
        # callback method for ways
        for osmid, tags, pos in nodes:
                self.n[osmid] = {}
                self.n[osmid]['tags'] = tags
                self.n[osmid]['pos'] = pos
                #print "node:",osmid, tags, pos

    def get_map_bound(self):
        l = 666
        ll = 666
        lm = 666
        llm = 666
        for k in self.n:
                if self.n[k]['pos'][0]>l or l==666:
                        l= self.n[k]['pos'][0]
                if self.n[k]['pos'][0]<lm or lm==666:
                        lm= self.n[k]['pos'][0]
                if self.n[k]['pos'][1]>ll or ll==666:
                        ll= self.n[k]['pos'][1]
                if self.n[k]['pos'][1]<llm or llm==666:
                        llm= self.n[k]['pos'][1]
        return (l,ll,lm,llm)
   def get_relative_coord(self,bound, node):
        return (self.n[node]['pos'][0]-bound[2],self.n[node]['pos'][1]-bound[3])

W = 1920
H = 1280

h = DataHandler()
print "Loading database in memory"
p = OSMParser(concurrency=3, ways_callback=h.ways, nodes_callback=h.nodes)
p.parse("ile-de-france-150801.osm.pbf")
#p.parse('alsace-150901.osm.pbf')
print "Database loaded","ways: ",len(h.w),"nodes: ",len(h.n)
process = psutil.Process(os.getpid())
print process.memory_info().rss/(1024*1024),"Mo"
print "Get map bound.."
bound = h.get_map_bound()
ratiox = W/(bound[0]-bound[2])
ratioy = H/(bound[1]-bound[3])
print "map bound = ",bound, "display ratio",ratiox,ratioy


img = Image.new("RGB", (W, H), "black")
draw = ImageDraw.Draw(img)
i=0
for k in h.n:
        pt = h.get_relative_coord(bound,k)
        draw.point((pt[0]*ratiox,pt[1]*ratioy), fill="white")
        i=i+1
        if i%1000==0:
                print "Progress:",i,"on ",len(h.n)

img.save("img.png", "PNG")
  D'accord, c'est hideux, c'est nul... mais ça m'a pris 5 minutes chronos pour voir que j'arrive à charger des données cohérentes ! Le get_map_bound sert a récupérer la latitude et longitude min et max des données. On remarque que dans les régions les gens ont mis des gros morceaux d'autoroute qui sortent. Après on fait un . par node, c'est beaucoup plus rapide que ce qu'il en parait a première vue ! La prochaine fois je fais plus propre et j'ajoute des fonctions qui vont commencer à donner quelque chose d'utile... et de plus sympa !    

Related Post

Partagez..Share on FacebookTweet about this on TwitterShare on Google+Share on RedditShare on TumblrPin on PinterestPrint this pageEmail this to someone

Laisser un commentaire

Votre adresse de messagerie ne sera pas publiée. Les champs obligatoires sont indiqués avec *