Ñò
Rá¬Pc           @   s@  d  Z  d d k Z d d k Td d k l Z d d k Z e i d ƒ Z d e f d „  ƒ  YZ	 d e f d	 „  ƒ  YZ
 d
 e f d „  ƒ  YZ d e f d „  ƒ  YZ d f  d „  ƒ  YZ d e f d „  ƒ  YZ d e f d „  ƒ  YZ d e f d „  ƒ  YZ e d j o;d d k i i Z e ƒ  Z e i d ƒ e e ƒ GHe i d d d d d d d d d  d! g
 ƒ e i d d f d" d# ƒe i d d f d" d$ ƒe i d d f d" d% ƒe i d d f d" d& ƒe i d d f d" d' d( d) ƒe i d d  d! d d d f ƒ e i e ƒ GHHd* d+ GHd, e i ƒ  GHd- e i ƒ  GHd. e i d ƒ GHd/ e i  d ƒ GHd0 g  Z! e i" d ƒ D] Z# e! e# d1 qr[! GHd2 e i$ ƒ  GHd3 e i% ƒ  GHd4 e e ƒ GHe i& d5 ƒ Hd6 GHd, e i ƒ  GHd- e i ƒ  GHd2 e i$ ƒ  GHd4 e e ƒ GHe i' d d f ƒ Hd7 GHd, e i ƒ  GHd- e i ƒ  GHd2 e i$ ƒ  GHd4 e e ƒ GHe i' d d f ƒ Hd8 GHd, e i ƒ  GHd- e i ƒ  GHd2 e i$ ƒ  GHd4 e e ƒ GHHd9 GHe i( d ƒ Z) e e) ƒ GHd: e) i* d d  f ƒ GHd; e) i+ d d  d f ƒ GHd< e) i+ e) i, d g ƒ GHd= e) i- d! d g ƒ GHn d S(>   sá  
BASIC GRAPH CLASS
***********************************
*** 
*** BASIC GRAPH CLASS
*** 
*** written by Markus Doering
***    BGBM, Berlin, 2003
*** 
***********************************
$RCSfile: graph.py,v $
$Revision: 1231 $
$Author: j.holetschek $
$Date: 2012-11-21 15:12:34 +0100 (Mi, 21. Nov 2012) $

Some classes used for the graph class, a basic class for undirected graphs.
It stores the graph as a matrix with the matrix values being a dictionary if filled and None if not.
iÿÿÿÿN(   t   *(   t   uniques   pywrapper.grapht   NodeNotExistingErrorc           B   s   e  Z d  Z d „  Z RS(   sI   Exception raised when trying to reference a non existing node of a graph.c         C   s   t  i |  ƒ d  S(   N(   t	   Exceptiont   __init__(   t   self(    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR   "   s    (   t   __name__t
   __module__t   __doc__R   (    (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR       s   t   NodeAlreadyExistingErrorc           B   s   e  Z d  Z d „  Z RS(   sH   Exception raised when trying to add an already existing node of a graph.c         C   s   t  i |  ƒ d  S(   N(   R   R   (   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR   &   s    (   R   R   R   R   (    (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR	   $   s   t   EdgeNotExistingErrorc           B   s   e  Z d  Z d „  Z RS(   sI   Exception raised when trying to reference a non existing edge of a graph.c         C   s   t  i |  ƒ d  S(   N(   R   R   (   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR   *   s    (   R   R   R   R   (    (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR
   (   s   t   EdgeAlreadyExistingErrorc           B   s   e  Z d  Z d „  Z RS(   sH   Exception raised when trying to add an already existing edge of a graph.c         C   s   t  i |  ƒ d  S(   N(   R   R   (   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR   .   s    (   R   R   R   R   (    (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR   ,   s   t   graphc           B   s7  e  Z d  Z d „  Z d „  Z d „  Z d „  Z d „  Z d „  Z d „  Z	 d „  Z
 d	 „  Z d
 „  Z d „  Z h  d! d „ Z d „  Z d „  Z d „  Z d „  Z d „  Z d „  Z d „  Z d „  Z d „  Z d „  Z d „  Z d „  Z h  d „ Z d „  Z d „  Z d „  Z d „  Z  d „  Z! d „  Z" d  „  Z# RS("   s‰   A basic class for undirected graphs. It stores the graph as a matrix with the matrix values being a dictionary if filled and None if not.c         C   s   t  g  ƒ |  _ h  |  _ d  S(   N(   t   symmetricMatrixt   matrixt   edges(   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR   7   s    c         C   s+   y |  i  i | ƒ Wn t ƒ  ‚ n Xd S(   s(   add one node to the graph without edges.N(   R   t   addRowR	   (   R   t   node(    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   addNode=   s    c         C   s"   x | D] } |  i  | ƒ q Wd S(   s!   add a list of nodes to the graph.N(   R   (   R   t   nodesR   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   addNodesD   s     c      	   C   st   y] g  } |  i  | ƒ D] } | | d q ~ } x | D] } |  i | =q8 W|  i i | ƒ Wn t ƒ  ‚ n Xd S(   s8   remove node from graph. also remove all connected edges.i    N(   t   listAdjacentEdgesR   R   t   delRowR   (   R   R   t   _[1]t   et   adjEdgest   edgename(    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   delNodeI   s    . c         C   s   |  i  i i | ƒ p d Sd S(   Ni    i   (   R   t   _colst   has_key(   R   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt
   nodeExistsS   s    c         C   s   |  i  i ƒ  S(   s3   return a list of all nodes (vertices) of the graph.(   R   t   listRows(   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt	   listNodesX   s    c         C   sv   g  } |  i  i | ƒ } xW | i ƒ  D]I \ } } t | ƒ t h  ƒ j o$ t | ƒ d j o | i | ƒ q% q% W| S(   s   List all adjacent nodes.i    (   R   t   getRowt   itemst   typet   lent   append(   R   R   t   adjNodest   rowDictt   colR   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   listAdjacentNodes\   s     ,c         C   s&   g  |  _  |  i | |  i h  ƒ |  i  S(   s,   List all nodes that are connected to "node".(   t   _tmpt   DepthFirstSearcht
   _listNodes(   R   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   listConnectedNodese   s    	c         C   sR   h  } x |  i  ƒ  D] } d | | <q Wx |  i | ƒ D] } | | =q7 W| i ƒ  S(   s0   List all nodes that are NOT connected to "node".i   (   R    R-   t   keys(   R   R   t
   unconNodest   n(    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   listUnconnectedNodesk   s      c         C   s‰   g  } x| |  i  i ƒ  D]k } |  i  i | ƒ } d } x, | i ƒ  D] } | d j o d } PqA qA W| d j o | i | ƒ q q W| S(   sH   return a list of isolated nodes, that is nodes not connected with edges.i    i   N(   R   R   R!   t   valuest   NoneR%   (   R   t   isolatedNodesR   R'   t   isolatedt   value(    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   listIsolatedNodesv   s      	c         C   s<   | d } x+ | d D] } |  i  | | f ƒ | } q Wd S(   sl   connects several nodes at once, setting the edge value-dictionary to en empty dict and autonaming the edges.i    i   N(   t   addEdge(   R   R   t   firstt   last(    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   addPath†   s
    
 c         C   s  | d j o{ g  } xA |  i i ƒ  D]0 } t | ƒ t d ƒ j o | i | ƒ q# q# Wt | ƒ d j o t | ƒ d } qˆ d } n |  i i | ƒ o t ƒ  ‚ n` | |  i | <|  i	 i
 | ƒ } t | ƒ t d ƒ j o
 h  } n | | | <|  i	 i | | ƒ | S(   s£   adds an edge "name" between node1 and node2 with the relation value of "value". Naming edges is optional, leaving out edge-names will result in autonumbering them.i   i    N(   R3   R   R.   R#   R%   R$   t   maxR   R   R   t   gett   set(   R   R   R6   t   namet   oldIntEdgest   edget   EdgeDict(    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR8      s$     


c         C   s   |  i  S(   sG   return dictionary of all existing edges with their nodetuple as values.(   R   (   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt	   listEdges¥   s    c         C   s(   | \ } } |  i  i | | f ƒ i ƒ  S(   s-   return a list of all edges between two nodes.(   R   R=   R.   (   R   t   .1t   node1t   node2(    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   listEdgesBetweenNodes©   s    	c         C   s€   g  } |  i  i | ƒ } xa | i ƒ  D]S \ } } t | ƒ t h  ƒ j o. x+ | i ƒ  D] } | i | | f ƒ qW Wq% q% W| S(   s<   list all edges of one node as tuples (edge-name, other-node)(   R   R!   R"   R#   R.   R%   (   R   R   R   R'   R(   R   RA   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR   ­   s      c         C   s>   y |  i  | } Wn t ƒ  ‚ n X|  i i | ƒ | | f S(   sF   return tuple of 1.value of edge "name" and 2.tuple of connected nodes.(   R   R
   R   R=   (   R   R?   t	   nodeTuple(    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   getEdge·   s
    c         C   sg   |  i  i | ƒ p t ƒ  ‚ nD |  i  | } |  i  | =|  i i | ƒ } | | =|  i i | | ƒ d S(   s   delete edge "name".N(   R   R   R
   R   R=   R>   (   R   R?   R   RB   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   delEdge¿   s    
c         C   sc   g  } |  i  i | ƒ } t | ƒ t h  ƒ j o | i ƒ  } n x | D] } |  i | ƒ qH Wd S(   s,   delete all edges between two adjacent nodes.N(   R   R=   R#   R.   RJ   (   R   R   t
   edgesToDelR   RA   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt	   cut2NodesÊ   s     c         C   s‘   |  i  ƒ  o t ƒ  ‚ nt t ƒ  } t i |  i ƒ } | | _ t i |  i ƒ } | | _ | | _ x$ |  i | ƒ D] } | i	 | ƒ qr W| Sd  S(   N(
   t   hasClosedWalkt   CircleExistingErrort   treet   copyt   deepcopyR   R   t   rootR1   R   (   R   RR   t   treeObjt	   newMatrixR   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   makeTreeÔ   s    				 c         C   s`   |  i  i | ƒ } d } xA | i ƒ  D]3 } t | ƒ t h  ƒ j o | t | ƒ 7} q% q% W| S(   s8   return the degree (number of edges connected) of a node.i    (   R   R!   R2   R#   R$   (   R   R   t   rowt   degreeR(   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyRW   ã   s     c         C   sV   xO |  i  ƒ  D]A } |  i | ƒ d j o% |  i | | h  ƒ d j o d Sq q Wd S(   sd   returns 1 if the graph allows circular walks - that is its number of possible spanning trees is > 1.i   i    (   R    RW   t   _testClosed(   R   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyRM   í   s     c         C   s   d S(   sH   returns 1 if the graph is connected, that is if all nodes are connected.N(    (   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   isConnected÷   s    c         C   sŒ   | g } h  } xv t  | ƒ d j ob | i d ƒ } d | | <| | ƒ x8 |  i | ƒ D]' } | i | ƒ p | i | ƒ qX qX Wq Wd S(   s\   Traverse the graph in breadth-first search order and apply the function func to every node..i    i   N(   R$   t   popR)   R   R%   (   R   t   startt   funct   queuet   seenR   t   neighbor(    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   BreadthFirstSearchý   s    	 

 c         C   s   |  i  i | ƒ d  S(   N(   R*   R%   (   R   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR,   	  s    c         C   sY   d | | <| | ƒ x> |  i  | ƒ D]- } | i | ƒ p |  i | | | ƒ q$ q$ Wd S(   sZ   Traverse the graph in depth-first search order and apply the function func to every node..i   N(   R)   R   R+   (   R   R[   R\   t   _visitedR   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR+     s    

 c         C   s   d S(   su   find the shortest possible path of two nodes using the single-source or all-pair shortest path (SSSP/APSP) algorithm.N(    (   R   RE   RF   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   shortestPath  s    c         C   s   d S(   sC   find the minimum spanning tree using Kruskal's or Prim's algorithm.N(    (   R   RE   RF   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   minimumSpanningTree  s    c         C   s   d S(   s   find the Euler path.N(    (   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt	   EulerPath  s    c         C   s   d S(   s   find the Euler path.N(    (   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   HamiltonianPath   s    c         C   s   |  i  i d |  i ƒ  S(   s)   return simple string output of the graph.s   : (   t	   __class__R   t   __reprGraph__(   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   __repr__&  s    c         C   sm   d } x" |  i  ƒ  D] } | | d 7} q Wx; |  i i ƒ  D]* \ } } | | d d | d d 7} q; W| S(   s)   return simple string output of the graph.t    s   , i    t   -i   (   R7   R   R"   (   R   t   resultR   RA   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyRg   *  s      "c         C   s‘   |  i  | ƒ } x{ | D]s } | i | d ƒ pY | d | j o d S| i ƒ  } d | | d <|  i | | d | ƒ d j o d Sq q Wd S(   s(   recursive testing function for each nodei    i   (   R   R   RP   RX   (   R   t	   startNodet   currNodet   dictOfUsedEdgesR   RA   t   newDict(    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyRX   4  s      	N($   R   R   R   R   R   R   R   R   R    R)   R-   R1   R7   R;   R3   R8   RC   RG   R   RI   RJ   RL   RU   RW   RM   RY   R`   R,   R+   Rb   Rc   Rd   Re   Rh   Rg   RX   (    (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR   5   sB   				
											
			
		
	
									
RN   c           B   s   e  Z d  Z d „  Z RS(   sP   Exception raised when trying to change the tree into a graph containing circles.c         C   s   t  i |  ƒ d  S(   N(   R   R   (   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR   M  s    (   R   R   R   R   (    (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyRN   K  s   t   RootMissingErrorc           B   s   e  Z d  Z d „  Z RS(   sP   Exception raised when trying to change the tree into a graph containing circles.c         C   s   t  i |  ƒ d  S(   N(   R   R   (   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR   Q  s    (   R   R   R   R   (    (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyRp   O  s   RO   c           B   sV   e  Z d  Z d „  Z h  d d „ Z d „  Z d „  Z g  d „ Z d „  Z	 d „  Z
 RS(	   t   .c         C   s   t  i |  ƒ d  |  _ d  S(   N(   R   R   R3   RR   (   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR   W  s    c         C   sP   |  } t  i | | | | ƒ | i ƒ  o t ƒ  ‚ n t  i |  | | | ƒ d S(   s>   add edge, but check first if graph is still a tree afterwards.N(   R   R8   RM   RN   (   R   R   R6   R?   t	   testGraph(    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyR8   [  s
    c         C   sŸ   | \ } } |  i  | ƒ d j o t ƒ  ‚ n |  i  | ƒ d j o t ƒ  ‚ n | g } | | j o | g S|  i | | | ƒ } | d j o | Sg  Sd S(   s?   return a path (list of nodes) with all nodes between two given.i    N(   R   R   t   _DFSSearchNodeR3   (   R   RD   R[   t   endt   nodesVisitedRk   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   pathBetween2Nodesd  s    		c         C   sH   | d } g  } x+ | d D] } | |  i  | | f ƒ 7} q Wt | ƒ S(   s9   return a path (list of nodes) connecting all nodes given.i    i   (   Rv   R   (   R   R   R[   Rk   t   next(    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   pathConnectingNodess  s    
 c   	      C   sæ   |  i  d j o t ƒ  ‚ n g  } |  i  g g } t | ƒ } x- | D]% } | i |  i |  i  | f ƒ ƒ qE Wxk t t g  } | D] } | t | ƒ q‚ ~ ƒ ƒ D]6 } x- | D]% } y | i | | ƒ Wq¯ q¯ Xq¯ Wq¢ Wt | ƒ S(   sŸ   return a list of tuples (node/edge-value) connecting all nodes given to the root node. 
        Order them from root downwards according to distance from root.N(	   RR   R3   Rp   R   R%   Rv   t   rangeR<   R$   (	   R   R   Rk   t   pathsR   R   t   xt   deptht   path(    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt    listOrderedNodesConnectedViaRoot{  s"     #4  c         C   s   d |  i  d |  i ƒ  S(   Ns   Rooted Tree (s   ): (   RR   Rg   (   R   (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyRh     s    c         C   s‰   x‚ |  i  | ƒ D]q } | | j o | i | ƒ | S| | j o? | } | i | ƒ |  i | | | ƒ } | d  j o | Sq q Wd  S(   N(   R)   R%   Rs   R3   (   R   Rm   t   endNodet   visitedNodesR   t   NewVisitedNodest   deeper(    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyRs   ”  s     N(   R   R   R   R   R3   R8   Rv   Rx   R~   Rh   Rs   (    (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyRO   U  s   					t   __main__t   heiot   markust   piat   briant   silket   petert   stefant   ewaldt   melittat   irenet   paulR6   t   verliebtt   ext   geschwisters   schlimm verliebts   bald verliebtR?   t   SilBriRj   iP   s   All Nodes %ss   All Edges %ss   Degree(markus): %is   adjacentNodes(markus): %ss   adjacentEdges(pia): %si    s   graph has a closed walk ? %is   isolated nodes: %ss   print graph: %si   s   deleted edge 1s   cut off nodes silke & brians   cut off nodes silke & silkes   ##### TREE NOW !!! #####s   markus-irene: %ss   markus-irene-silke: %ss   root brian: %ss   root-ordered paul,brian: %s(.   R   RP   t   biocase.wrapper.graph.matrixt   biocase.tools.various_functionsR   t   loggingt	   getLoggert   logR   R   R	   R
   R   R   RN   Rp   RO   R   t   biocase.tools.showobjectt   toolst
   showobjectt   objt   gR   t   strR   R8   R;   t   viewR    RC   RW   R)   R   R   R   RM   R7   RJ   RL   RU   t   tRv   Rx   RR   R~   (    (    (    sC   /srv/www/vhosts/sammlung/BioCase/lib/biocase/wrapper/graph/graph.pyt   <module>   s„   
	ÿ P	+	1