ini parser (noch nicht fertig)

Code-Stücke können hier veröffentlicht werden.
Antworten
lost_mind
User
Beiträge: 82
Registriert: Dienstag 13. Februar 2007, 11:55

Hi (kann man hier auch unfertige sachen posten ? wen nicht sry)
ich weis es ist noch sehr unfertig und die tuple rückgabe :oops:
aber ich stelle es einfach mal hier rein ach ja kritik ist sehr erwünscht
das ist jetzt mein 3 projekt (btw. alle 3 sind noch unfertig :roll: )
das habe ich geschrieben weil ich mich ein wenig mit dem parsen beschäftigen wollte (auch wen ein ini parser nicht besonders schwer ist ...)
jedenfalls hier der code :)
ach ja er funzt kann aber zur zeit nur ini dateien laden speichern kommt noch und in die ini darf nur f = f aufgebaut sein wen sowas wie [base config] drin ist crasht das modul. Aber das werde ich übers wochende beheben und hoffentlich fertig schreiben :D

hier der code
das zweite argument bei load darf dict(oder einfach d) sein oder lis(oder einfach l) um das zurückgeben object zu bestimmen je nachdem was man will :)

wie gesagt die save funktion nicht benutzen :o

hier noch ein beispiel

Code: Alles auswählen

import IniParser
p = IniParser.Parser()
p.load("pfad", "dict")

Code: Alles auswählen

# -*- coding: utf-8 -*- 
#!usr/bin/env python    

class Parser(object):
    
    def __init__(self):
        self.config = None
        self.inifile = None
        self.objekt_type = None

    def load(self, inifile, type="dict"):
        self.inifile = inifile
        self.loadinifile()
        self.del_spaces()
        self.seperate()
        self.return_type(type)
        return self.config
        del self.inifile
    
    def save(self, path, config_object):
        self.get_type(config_object)
    
    def loadinifile(self):
        self.inifile = file(self.inifile, 'rb')
        self.inifile = self.inifile.read()
    
    def del_spaces(self):
        self.inifile = self.inifile.replace(" ", "")
    
    def seperate(self):
        self.inifile = self.inifile.splitlines()
        
    def return_type(self, type):
        if type == "dict" or type == "d":
            self.return_dic()
        #elif type == "tuple":
        #    self.return_tuple()
        elif type == "list" or type == "l":
            self.return_list()
    
    def return_dic(self):
        self.config = {}
        for config in self.inifile:
            c = config.split('=')
            self.config[c[0]] = c[1]
            del c

    def return_tuple(self):
        self.config = ()
        for config in self.inifile:
            c = config.split('=')
            self.config = ((c[0], c[1]))
            del c
            
    def return_list(self):
        self.config = []
        for config in self.inifile:
            c = config.split('=')
            self.config.append([c[0], c[1]])
            del c
            
    def get_type(self, config_object):
        if type(config_object) is dict:
            self.save_dict(config_object)
        elif type(config_object) is list:
            self.save_list(config_object)
                        
BlackJack

Der Quelltext ist sehr verwirrend. Zuviele Methoden die sehr wenig tun und zum grössten Teil nicht dazu gedacht sind, jemals von aussen aufgerufen zu werden.

Es wird immer auf den Attributen operiert, auch da wo Funktionen mit Rückgabewerten sauberer wären. Die Namen sind zum Grossteil irreführend und es werden die selben Namen/Attribute für grundverschiedene Typen verwendet. Das kann man innerhalb einer Funktion mal machen, wo es niemand anders mitbekommt, aber bei öffentlichen Attributen an den selben Namen mal ein Dateiobjekt und mal eine Zeichenkette zu binden, ist kein guter Stil. Man muss dann beim Programmieren immer im Kopf behalten wann denn nun welcher Typ dort zu erwarten ist.

Die ``del``-Anweisungen sind allesamt überflüssig, die in `load()` wird sogar niemals ausgeführt.

Warum die letzte Methode `get_type()` heisst, ist unverständlich.

Diese `return_type`-Geschichte trägt einiges zur Verwirrung bei. Wenn man sowieso beim Aufruf entscheiden muss, was man haben möchte, dann braucht man das Argument nicht, sondern kann gleich die passende Methode aufgerufen. In beiden Fällen sollte man gemeinsamen Quelltext nur einmal schreiben. `return_dic()` und `return_list()` sind nahezu identisch. Und wenn man dort jetzt zusätzlichen Code einfügen wollte, etwa um Kommentar- und Leerzeilen in der Ini-Datei zu ignorieren, müsste man den selben Quelltext in beiden Methoden ergänzen.

Letztendlich wäre für diesen Code auch eine Handvoll Funktionen ausreichend. Die Klasse ist nicht nötig.

Im Grunde ist die ganze Funktionalität der Klasse mit diesen beiden kleinen Funktionen erschlagen:

Code: Alles auswählen

def iparse_ini(lines):
    for line in lines:
        line = line.strip().replace(' ', '')
        yield tuple(line.split('=', 1))


def load_ini(filename, return_type=dict):
    ini_file = open(filename, 'r')
    result = return_type(iparse_ini(ini_file))
    ini_file.close()
    return result


def main():
    print load_ini('test.ini')
    print load_ini('test.ini', list)
lost_mind
User
Beiträge: 82
Registriert: Dienstag 13. Februar 2007, 11:55

Da dachte ich ich hab einen halbwegs brauchbaren code geschrieben und dan .. naja also das sie von ausen aufrufbar sind hätte ich noch am WE geändert das nach return nichts mehr ausgeführt wird wusste ich nicht und die vielen funktionen hm eigentlich dachte ich so ist es besser alls wen ich zuviel funktionalität in eine funktion packe. und ich hab das auch gemacht weil ich in nem buch gelesen hab das es besser ist jeden schrit in eine funktion zu packen. naja jedenfalls thx dan werde ich wohl am besten von scratch nochmal neu beginnen mit hilfe deines beispiels.
EyDu
User
Beiträge: 4881
Registriert: Donnerstag 20. Juli 2006, 23:06
Wohnort: Berlin

Wenn du dein Modul nur zu Übung schreibst macht neu anfangen vielleicht Sinn, aber wenn man einen INI-Parser benötigt, ist man mit dem Standard-Modul "ConfigParser" wohl bestens bedient.
lost_mind
User
Beiträge: 82
Registriert: Dienstag 13. Februar 2007, 11:55

jep ist ist nur zur übung und weil ich mich ein wenig mit parsen beschäftigen wollte auch wenn ich nichts vom ConfigParser gewusst habe :oops:
Antworten