def convertNormalNetwork(n):
     """ convert a normal network into a decomposable one """
     if isinstance(n, RecurrentNetwork):
         res = RecurrentDecomposableNetwork()
         for c in n.recurrentConns:
             res.addRecurrentConnection(c)
     else:
         res = FeedForwardDecomposableNetwork()
     for m in n.inmodules:
         res.addInputModule(m)
     for m in n.outmodules:
         res.addOutputModule(m)
     for m in n.modules:
         res.addModule(m)
     for c in combineLists(list(n.connections.values())):
         res.addConnection(c)
     res.name = n.name
     res.sortModules()
     return res
Example #2
0
    def _topologicalSort(self):
        """Update the network structure and make .modulesSorted a topologically
        sorted list of the modules."""
        # Algorithm: R. E. Tarjan (1972), stolen from:
        #     http://www.bitformation.com/art/python_toposort.html

        # Create a directed graph, including a counter of incoming connections.
        graph = {}
        for node in self.modules:
            if node not in graph:
                # Zero incoming connections.
                graph[node] = [0]
        for c in combineLists(list(self.connections.values())):
            graph[c.inmod].append(c.outmod)
            # Update the count of incoming arcs in outnode.
            graph[c.outmod][0] += 1

        # Find all roots (nodes with zero incoming arcs).
        roots = [
            node for (node, nodeinfo) in list(graph.items())
            if nodeinfo[0] == 0
        ]

        # Make sure the ordering on all runs is the same.
        roots.sort(key=lambda x: x.name)

        # Repeatedly emit a root and remove it from the graph. Removing
        # a node may convert some of the node's direct children into roots.
        # Whenever that happens, we append the new roots to the list of
        # current roots.
        self.modulesSorted = []
        while len(roots) != 0:
            root = roots[0]
            roots = roots[1:]
            self.modulesSorted.append(root)
            for child in graph[root][1:]:
                graph[child][0] -= 1
                if graph[child][0] == 0:
                    roots.append(child)
            del graph[root]

        if graph:
            raise NetworkConstructionException("Loop in network graph.")
Example #3
0
    def __str__(self):
        sortedByName = lambda itr: sorted(itr, key=lambda i: i.name)

        params = {
            'name':
            self.name,
            'modules':
            self.modulesSorted,
            'connections':
            sortedByName(
                combineLists([
                    sortedByName(self.connections[m])
                    for m in self.modulesSorted
                ])),
        }

        s = ("%(name)s\n" + "   Modules:\n    %(modules)s\n" +
             "   Connections:\n    %(connections)s\n") % params

        return s