# -*- coding: utf-8 -*- import re import xml.dom.minidom import os try: import pygraphviz as pgv except ImportError: pgv = None def parse_multi_value_node(node): 'convert multi value node like to dictionary {N:10000, Nx:100, Ny:100}' value_dict = dict() for key in node.attributes.keys(): value_dict[key] = try_convert_value_string(node.getAttribute(key)) return value_dict def parse_value_node(element_value_node): value = element_value_node.getAttribute("value") if value != "": # simple value node like return try_convert_value_string(value) else: # value node with multiple attributes like return parse_multi_value_node(element_value_node) def try_convert_value_string(value_string): v = value_string try: v = int(value_string) except: try: v = float(value_string) except: pass return v class SimElement: def __init__(self, name="", id=0, type=0, xml_node=None, dir_name=None): self.id = id self.type = type self.name = name self.dir_name = dir_name if xml_node is not None: self.name = xml_node.getAttribute("Name") self.type = try_convert_value_string(xml_node.getAttribute("Type")) self.id = try_convert_value_string(xml_node.getAttribute("id")) childs = xml_node.childNodes for child in childs: if child.localName is not None: value = parse_value_node(child) setattr(self, child.localName, value) class Layer(SimElement): def __init__(self, name="", id=0, type=0, xml_node=None, dir_name=None): SimElement.__init__(self, name=name, id=id, type=type, xml_node=xml_node, dir_name=dir_name) class Connection(SimElement): def __init__(self, name="", id=0, type=0, xml_node=None, dir_name=None): SimElement.__init__(self, name=name, id=id, type=type, xml_node=xml_node, dir_name=dir_name) class Normalize(SimElement): def __init__(self, name="", id=0, type=0, xml_node=None, dir_name=None): SimElement.__init__(self, name=name, id=id, type=type, xml_node=xml_node, dir_name=dir_name) class Input(SimElement): def __init__(self, name="", id=0, type=0, xml_node=None, dir_name=None): SimElement.__init__(self, name=name, id=id, type=type, xml_node=xml_node, dir_name=dir_name) def get_SimElement_list_from_dom(dom, tag_name=None, class_name=None, dir_name=None): element_list = [] dom_elements = dom.getElementsByTagName(tag_name) for node in dom_elements: element_list.append(class_name(xml_node=node, dir_name=dir_name)) return element_list class SimInfo: "read Sim.SimInfo file from simulation data directory" def __init__(self, file_name): file = open(file_name, "r") dat = file.read() file.close() self.dom = xml.dom.minidom.parseString(dat) self.dir_name = os.path.dirname(file_name) self.layers = get_SimElement_list_from_dom(self.dom, "Layer", Layer) self.normalizes = get_SimElement_list_from_dom(self.dom, "Normalize", Normalize) self.connections = get_SimElement_list_from_dom(self.dom, "Connection", Connection) self.inputs = get_SimElement_list_from_dom(self.dom, "Input", Input) def get_layers(self): return self.layers def get_normalizes(self): return self.normalizes def get_connections(self): return self.connections def get_inputs(self): return self.inputs def find_layer_with_id(self, id): for layer in self.layers: if layer.id == id: return layer def write_layout_graph(self, file_name="layout.png"): if pgv is None: raise ImportError("pygraphviz not available") G = pgv.AGraph(strict=False,directed=True) G.edge_attr['color'] = 'green' for layer in self.layers: G.add_node(layer.name) for con in self.connections: source = self.find_layer_with_id(con.Source['id']) target = self.find_layer_with_id(con.Target['id']) if source is not None and target is not None: G.add_edge(source.name, target.name) edge = G.get_edge(source.name, target.name) if con.InputNumber in [1,3]: edge.attr['arrowhead'] = 'tee' edge.attr['color'] = 'red' G.layout(prog='dot') G.draw(file_name) class ConfigLineParser: "parse line of a config file" def __init__(self): self.re_comment = re.compile("#") self.re_key_value = re.compile("([a-zA-Z0-9_]+) : (.*)") self.re_flag = re.compile("([a-zA-Z0-9_]+)") self.re_flag_false = re.compile("No([a-zA-Z0-9_]+)") def parse_line(self, line): if self.re_comment.match(line) is not None: return None, None match = self.re_key_value.match(line) if match is not None: key = match.group(1) value = match.group(2) return key, try_convert_value_string(value) match = self.re_flag_false.match(line) if match is not None: key = match.group(1) return key, False match = self.re_flag.match(line) if match is not None: key = match.group(1) return key, True return None, None def read_config(file_path): "read simulation settings file (settings_.cfg or /backup_settings)" config_dict = dict() file = open(file_path, 'r') parser = ConfigLineParser() for line in file: key, value = parser.parse_line(line) if key is not None: config_dict[key] = value file.close() return config_dict if __name__=="__main__": pass