Saturday, March 1, 2014

Miglioramento del codice

Lavorando in Python si apprezza la facilità con cui si colgono le imperfezioni del codice, quasi subito dopo averlo scritto. A volte sono puramente estetiche e basta seguire le indicazioni della PEP 8 (Python Enhancement Proposal) per ottenere un risultato migliore. Altre volte bisogna cogliere ridondanze e mancanza di snellezza del codice. Ora che ho verificato che il codice del post precedente funziona, posso iniziare a migliorarlo.

  1. trasferisco le importazioni delle librerie esterne fuori della classe
  2. limito le funzioni del costruttore alla inizializzazione dei file esterni
  3. riduco la ridondanza, spostando su una funzione la ricerca del pattern sulla stringa 'd' e creando una lista di pattern da leggere iterativamente. la funzione s_match restituisce sia la stringa risultante dal match pattern/stringa d, sia la stringa d modificata, per mezzo di una tupla
  4. affido l'esecuzione del programma al metodo re_load che gestisce anche le exception per le espressioni regolari

E questo è il risultato, un po' più pitonico:


#|/usr/bin/env python
import re
import xml.etree.ElementTree as ET

class SVG2Tk:
    
    def __init__(self, file_s, file_out):

        self.file_s = open(file_s, 'r')
        self.file_out= open(file_out,'w')
        self.tk_out = open('tk_out.txt','w')


    def s_match(self, pattern, d):
        matchObj = re.match(pattern, d)
        if matchObj:
            string = matchObj.group()
            d = d.replace(string, "")
            s_string = re.split(r'[;\s]*',string)
            string = ','.join(s_string[:-1])
            return (string, d)
        return None
    
    def xmlrecur(self,x):
        for i in x:
            if set(['id','style','d']).issubset(i.attrib):
                    self.file_out.write(i.attrib['id'])
                    self.file_out.write('\n')
                    self.file_out.write(i.attrib['style'])
                    self.file_out.write('\n')
                    self.file_out.write(i.attrib['d'])
                    self.file_out.write('\n')
            elif set(['width','height']).issubset(i.attrib):
                self.file_out.write(i.attrib['width'])
                self.file_out.write('\n')
                self.file_out.write(i.attrib['height'])
                self.file_out.write('\n')
                
            else:
                self.xmlrecur(i)

    def re_load(self, file_out):

        tree = ET.parse(self.file_s)
        root = tree.getroot()
        self.xmlrecur(root)
        self.file_out.close()
        
        self.file_in = open(file_out, 'r')
        
        try:
            width=self.file_in.next()
            height=self.file_in.next()
            self.tk_out.write('width %sheight %s' % (width, height))
        except Exception:
            print Exception

        while True:
            
            try:
                id_ = self.file_in.next()
                style = self.file_in.next()
                d = self.file_in.next()

                self.tk_out.write('id,' + id_)
                pattern=[
                r'([M]{1}[\s]*[-\d]*[\.]?[\d]*[\,\s]?[-\d]*[\.]?[\d]*[\s]*)',
                r'([L]{1}[\s]*[-\d]*[\.]?[\d]*[\,\s]{1}[-\d]*[\.]?[\d]*[\s]*)',
                r'([C]{1}[\s]*)(([-\d]*[\.]?[\d]*[\,\s]{1}[-\d]*[\.]?[\d]*[\s]*){3})',
                r'([z]{1}[\s]*)'
                ]
                
                while len(d) > 0:
                    for p in pattern:
                        ret = self.s_match(p, d)
                        if ret != None:
                            string = ret[0]
                            d = ret[1]
                            self.tk_out.write(string+'\n')
                        
            except Exception:
                print Exception
                self.tk_out.close()
                break



if __name__ == '__main__':
    app = SVG2Tk('EU-Italy.svg','out_xml.txt')
    app.re_load('out_xml.txt')

Modificata così la classe, procederemo all'ultimo step, cioè alla traduzione in Tkinter.

No comments:

Post a Comment

How to create a virtual linux machine with qemu under Debian or Ubuntu with near native graphics performance

It's been a long time since my latest post. I know, I'm lazy. But every now and then I like to publish something that other people c...