lib/diGraph.c File Reference

#include "common.h"
#include "hash.h"
#include "dlist.h"
#include "diGraph.h"

Include dependency graph for diGraph.c:

Go to the source code of this file.

Functions

diGraphdgNew ()
static void dgNodeFree (struct dgNode **pNode)
static void dgNodeFreeList (struct dgNode **pList)
void dgFree (struct diGraph **pGraph)
dgNodedgAddNode (struct diGraph *dg, char *name, void *val)
dgNodedgAddNumberedNode (struct diGraph *dg, int id, void *val)
dgNodedgFindNode (struct diGraph *dg, char *name)
dgNodedgFindNumberedNode (struct diGraph *dg, int id)
void * dgNodeVal (struct dgNode *node)
void * dgNodeName (struct dgNode *node)
int dgNodeNumber (struct dgNode *node)
dgNodeRefdgFindNodeInRefList (struct dgNodeRef *refList, struct dgNode *node)
dgConnectiondgFindNodeInConList (struct dgConnection *conList, struct dgNode *node)
dgEdgedgConnect (struct diGraph *dg, struct dgNode *a, struct dgNode *b)
dgEdgedgConnectWithVal (struct diGraph *dg, struct dgNode *a, struct dgNode *b, void *val)
static struct dlNodedgRemoveFromConList (struct dgConnection **pConList, struct dgNode *node, struct dgConnection **retCon)
void dgDisconnect (struct diGraph *dg, struct dgNode *a, struct dgNode *b)
void dgClearVisitFlags (struct diGraph *dg)
void dgClearConnFlags (struct diGraph *dg)
static boolean rPathExists (struct dgNode *a)
boolean dgPathExists (struct diGraph *dg, struct dgNode *a, struct dgNode *b)
static void rTopoSort (struct dgNode *node)
void dgTopoSort (struct diGraph *dg)
static boolean rHasCycles (struct dgNode *node)
boolean dgHasCycles (struct diGraph *dg)
static void rFindConnected (struct dgNode *a)
dgNodeRefdgFindNextConnected (struct diGraph *dg)
dgNodeRefdgFindNextConnectedWithVals (struct diGraph *dg)
static int connectedComponents (struct diGraph *dg)
int dgConnectedComponents (struct diGraph *dg)
int dgConnectedComponentsWithVals (struct diGraph *dg)
dgNodeRefdgFindNewConnected (struct diGraph *dg, struct dgNode *a)
dgNodeRefdgFindNewConnectedWithVals (struct diGraph *dg, struct dgNode *a)
dgNodeRefdgFindConnectedToNode (struct diGraph *dg, struct dgNode *a)
dgEdgedgDirectlyFollows (struct diGraph *dg, struct dgNode *a, struct dgNode *b)
dgNodeRefdgFindPath (struct diGraph *dg, struct dgNode *a, struct dgNode *b)
static int cmpPriority (const void *va, const void *vb)
boolean dgParentsAllVisited (struct dgNode *node)
dgNodeRefdgConstrainedPriorityOrder (struct diGraph *dg)
dgEdgeRefdgFindSubEdges (struct diGraph *dg, struct dgNodeRef *subGraph)
void dgSwapEdges (struct diGraph *dg, struct dgEdgeRef *erList)
dgConnectiondgNextList (struct dgNode *node)
dgConnectiondgPrevList (struct dgNode *node)
void dgDumpGraph (struct diGraph *dg, FILE *out, boolean hideIsolated)

Variables

static char const rcsid [] = "$Id: diGraph.c,v 1.9 2005/08/17 03:01:29 galt Exp $"
static struct dgNoderTarget
static int topoIx
dgNodeRefrRefList
bool rMustHaveVal


Function Documentation

static int cmpPriority ( const void *  va,
const void *  vb 
) [static]

Definition at line 584 of file diGraph.c.

References dgNode::priority.

Referenced by dgConstrainedPriorityOrder().

00586 {
00587 const struct dgNode *a = *((struct dgNode **)va);
00588 const struct dgNode *b = *((struct dgNode **)vb);
00589 return (a->priority - b->priority);
00590 }

Here is the caller graph for this function:

static int connectedComponents ( struct diGraph dg  )  [static]

Definition at line 423 of file diGraph.c.

References dgNode::component, dgNode::conn, dgClearConnFlags(), dgNodeRef::next, dgNode::next, dgNodeRef::node, diGraph::nodeList, rFindConnected(), rMustHaveVal, rRefList, slFreeList(), and dgNode::val.

Referenced by dgConnectedComponents(), and dgConnectedComponentsWithVals().

00426 {
00427 struct dgNodeRef *ref;
00428 int conCount = 0;
00429 struct dgNode *a = dg->nodeList;
00430 
00431 dgClearConnFlags(dg);
00432 for (;;)
00433     {
00434     for (; a != NULL; a = a->next)
00435         {
00436         if (!a->conn && (!rMustHaveVal || a->val))
00437             break;
00438         }
00439     if (a == NULL)
00440         break;
00441     rRefList = NULL;
00442     rFindConnected(a);
00443     ++conCount;
00444     for (ref = rRefList; ref != NULL; ref = ref->next)
00445         {
00446         ref->node->component = conCount;
00447         }
00448     slFreeList(&rRefList);
00449     }
00450 return conCount;
00451 }

Here is the call graph for this function:

Here is the caller graph for this function:

struct dgNode* dgAddNode ( struct diGraph dg,
char *  name,
void *  val 
) [read]

Definition at line 56 of file diGraph.c.

References AllocVar, errAbort(), hashAdd(), hashLookup(), hashEl::name, dgNode::name, diGraph::nodeHash, diGraph::nodeList, ptrToLL, slAddHead, dgNode::val, and hashEl::val.

Referenced by dgAddNumberedNode().

00062 {
00063 struct dgNode *node;
00064 struct hashEl *hel;
00065 struct hash *hash = dg->nodeHash;
00066 char nbuf[17];
00067 
00068 if (name == NULL)
00069     {
00070     sprintf(nbuf, "%p", val);
00071     name = nbuf;
00072     }
00073 hel = hashLookup(hash, name);
00074 if (hel != NULL)
00075     {
00076     node = hel->val;
00077     if (node->val != val)
00078         {
00079         errAbort("Trying to add node %s with a new value (old 0x%llx new 0x%llx)",
00080             name, ptrToLL(node->val), ptrToLL(val));
00081         }
00082     return node;
00083     }
00084 AllocVar(node);
00085 hel = hashAdd(hash, name, node);
00086 node->name = hel->name;
00087 node->val = val;
00088 slAddHead(&dg->nodeList, node);
00089 return node;
00090 }

Here is the call graph for this function:

Here is the caller graph for this function:

struct dgNode* dgAddNumberedNode ( struct diGraph dg,
int  id,
void *  val 
) [read]

Definition at line 92 of file diGraph.c.

References dgAddNode().

00094 {
00095 char buf[16];
00096 sprintf(buf, "%d", id);
00097 return dgAddNode(dg, buf, val);
00098 }

Here is the call graph for this function:

void dgClearConnFlags ( struct diGraph dg  ) 

Definition at line 259 of file diGraph.c.

References dgNode::conn, FALSE, dgNode::next, and diGraph::nodeList.

Referenced by connectedComponents(), and dgFindConnectedToNode().

00261 {
00262 struct dgNode *node;
00263 for (node = dg->nodeList; node != NULL; node = node->next)
00264     node->conn = FALSE;
00265 }

Here is the caller graph for this function:

void dgClearVisitFlags ( struct diGraph dg  ) 

Definition at line 251 of file diGraph.c.

References FALSE, dgNode::next, diGraph::nodeList, and dgNode::visited.

Referenced by dgHasCycles(), dgPathExists(), and dgTopoSort().

00253 {
00254 struct dgNode *node;
00255 for (node = dg->nodeList; node != NULL; node = node->next)
00256     node->visited = FALSE;
00257 }

Here is the caller graph for this function:

struct dgEdge* dgConnect ( struct diGraph dg,
struct dgNode a,
struct dgNode b 
) [read]

Definition at line 158 of file diGraph.c.

References dgEdge::a, dgEdge::b, and dgConnectWithVal().

00162 {
00163 return dgConnectWithVal(dg, a, b, NULL);
00164 }

Here is the call graph for this function:

int dgConnectedComponents ( struct diGraph dg  ) 

Definition at line 453 of file diGraph.c.

References connectedComponents(), FALSE, and rMustHaveVal.

00456 {
00457 rMustHaveVal = FALSE;
00458 return connectedComponents(dg);
00459 }

Here is the call graph for this function:

int dgConnectedComponentsWithVals ( struct diGraph dg  ) 

Definition at line 461 of file diGraph.c.

References connectedComponents(), rMustHaveVal, and TRUE.

00465 {
00466 rMustHaveVal = TRUE;
00467 return connectedComponents(dg);
00468 }

Here is the call graph for this function:

struct dgEdge* dgConnectWithVal ( struct diGraph dg,
struct dgNode a,
struct dgNode b,
void *  val 
) [read]

Definition at line 166 of file diGraph.c.

References dgEdge::a, AllocVar, dgEdge::b, dgFindNodeInConList(), dlAddValTail(), diGraph::edgeList, dgConnection::edgeOnList, dgNode::name, dgNode::nextList, dgConnection::node, dgNode::prevList, slAddHead, dgEdge::val, dlNode::val, and warn().

Referenced by dgConnect().

00170 {
00171 struct dgConnection *con;
00172 struct dgEdge *edge;
00173 struct dlNode *edgeOnList;
00174 
00175 /* Check to see if it's already there. */
00176 if ((con = dgFindNodeInConList(a->nextList, b)) != NULL)
00177     {
00178     edge =  con->edgeOnList->val;
00179     if (val != edge->val)
00180         warn("Trying to add new value to edge between %s and %s, ignoring",
00181            a->name, b->name);
00182     return edge;
00183     }
00184 /* Allocate edge and put on list. */
00185 AllocVar(edge);
00186 edge->a = a;
00187 edge->b = b;
00188 edge->val = val;
00189 edgeOnList = dlAddValTail(dg->edgeList, edge);
00190 
00191 /* Connect nodes to each other. */
00192 AllocVar(con);
00193 con->node = b;
00194 con->edgeOnList = edgeOnList;
00195 slAddHead(&a->nextList, con);
00196 AllocVar(con);
00197 con->node = a;
00198 con->edgeOnList = edgeOnList;
00199 slAddHead(&b->prevList, con);
00200 
00201 return edge;
00202 }

Here is the call graph for this function:

Here is the caller graph for this function:

struct dgNodeRef* dgConstrainedPriorityOrder ( struct diGraph dg  )  [read]

Definition at line 604 of file diGraph.c.

References AllocVar, cmpPriority(), dgHasCycles(), dgParentsAllVisited(), dlAddValTail(), dlEmpty(), dlRemove(), dlSort(), errAbort(), FALSE, freeDlList(), freeMem(), dlList::head, newDlList(), dlNode::next, dgNode::next, diGraph::nodeList, slAddHead, slReverse(), TRUE, dlNode::val, and dgNode::visited.

00609 {
00610 struct dlList *sortedList = newDlList();
00611 struct dgNode *graphNode;
00612 struct dlNode *listNode;
00613 struct dgNodeRef *refList = NULL, *ref;
00614 
00615 if (dgHasCycles(dg))
00616     errAbort("Call to dgConstrainedPriorityOrder on graph with cycles.");
00617 
00618 /* Make up list sorted by priority. */
00619 for (graphNode = dg->nodeList; graphNode != NULL; graphNode = graphNode->next)
00620     {
00621     dlAddValTail(sortedList, graphNode);
00622     graphNode->visited = FALSE;
00623     }
00624 dlSort(sortedList, cmpPriority);
00625 
00626 /* Loop taking first member of list with no untraversed parents. */
00627 while (!dlEmpty(sortedList))
00628     {
00629     for (listNode = sortedList->head; listNode->next != NULL; listNode = listNode->next)
00630         {
00631         graphNode = listNode->val;
00632         if (dgParentsAllVisited(graphNode))
00633             {
00634             dlRemove(listNode);
00635             freeMem(listNode);
00636             AllocVar(ref);
00637             ref->node = graphNode;
00638             slAddHead(&refList, ref);
00639             graphNode->visited = TRUE;
00640             break;
00641             }
00642         }
00643     }
00644 freeDlList(&sortedList);
00645 slReverse(&refList);
00646 return refList;
00647 }

Here is the call graph for this function:

struct dgEdge* dgDirectlyFollows ( struct diGraph dg,
struct dgNode a,
struct dgNode b 
) [read]

Definition at line 499 of file diGraph.c.

References dgFindNodeInConList(), dgConnection::edgeOnList, dgNode::nextList, and dlNode::val.

00501 {
00502 struct dgConnection *con = dgFindNodeInConList(a->nextList, b);
00503 if (con == NULL)
00504     return NULL;
00505 return con->edgeOnList->val;
00506 }

Here is the call graph for this function:

void dgDisconnect ( struct diGraph dg,
struct dgNode a,
struct dgNode b 
)

Definition at line 233 of file diGraph.c.

References dgEdge::a, dgEdge::b, dgRemoveFromConList(), dlRemove(), freeMem(), dgNode::nextList, dgNode::prevList, and dlNode::val.

00235 {
00236 struct dlNode *edgeInList;
00237 struct dgEdge *edge;
00238 
00239 dgRemoveFromConList(&a->nextList, b, NULL);
00240 edgeInList = dgRemoveFromConList(&b->prevList, a, NULL);
00241 if (edgeInList != NULL)
00242     {
00243     edge = edgeInList->val;
00244     dlRemove(edgeInList);
00245     freeMem(edgeInList);
00246     freeMem(edge);
00247     }
00248 }

Here is the call graph for this function:

void dgDumpGraph ( struct diGraph dg,
FILE *  out,
boolean  hideIsolated 
)

Definition at line 722 of file diGraph.c.

References dgNode::name, dgConnection::next, dgNode::next, dgNode::nextList, dgConnection::node, and diGraph::nodeList.

00724 {
00725 struct dgNode *node;
00726 struct dgConnection *con;
00727 
00728 for (node = dg->nodeList; node != NULL; node = node->next)
00729     {
00730     if (hideIsolated  && node->nextList == NULL)
00731         continue;
00732     fprintf(out, "%s:", node->name);
00733     for (con = node->nextList; con != NULL; con = con->next)
00734         fprintf(out, " %s", con->node->name);
00735     fprintf(out, "\n");
00736     }
00737 }

struct dgNodeRef* dgFindConnectedToNode ( struct diGraph dg,
struct dgNode a 
) [read]

Definition at line 491 of file diGraph.c.

References dgClearConnFlags(), and dgFindNewConnected().

00494 {
00495 dgClearConnFlags(dg);
00496 return dgFindNewConnected(dg, a);
00497 }

Here is the call graph for this function:

struct dgNodeRef* dgFindNewConnected ( struct diGraph dg,
struct dgNode a 
) [read]

Definition at line 470 of file diGraph.c.

References FALSE, rFindConnected(), rMustHaveVal, and rRefList.

Referenced by dgFindConnectedToNode().

00473 {
00474 rRefList = NULL;
00475 rMustHaveVal = FALSE;
00476 rFindConnected(a);
00477 return rRefList;
00478 }

Here is the call graph for this function:

Here is the caller graph for this function:

struct dgNodeRef* dgFindNewConnectedWithVals ( struct diGraph dg,
struct dgNode a 
) [read]

Definition at line 480 of file diGraph.c.

References rFindConnected(), rMustHaveVal, rRefList, and TRUE.

00483 {
00484 rRefList = NULL;
00485 rMustHaveVal = TRUE;
00486 rFindConnected(a);
00487 return rRefList;
00488 }

Here is the call graph for this function:

struct dgNodeRef* dgFindNextConnected ( struct diGraph dg  )  [read]

Definition at line 380 of file diGraph.c.

References dgNode::conn, FALSE, dgNode::next, diGraph::nodeList, rFindConnected(), rMustHaveVal, and rRefList.

00387 {
00388 struct dgNode *a;
00389 
00390 for (a=dg->nodeList; a != NULL; a = a->next)
00391     {
00392     if (!a->conn)
00393         break;
00394     }
00395 if (a == NULL)
00396     return NULL;
00397 rRefList = NULL;
00398 rMustHaveVal = FALSE;
00399 rFindConnected(a);
00400 return rRefList;
00401 }

Here is the call graph for this function:

struct dgNodeRef* dgFindNextConnectedWithVals ( struct diGraph dg  )  [read]

Definition at line 403 of file diGraph.c.

References dgNode::conn, dgNode::next, diGraph::nodeList, rFindConnected(), rMustHaveVal, rRefList, TRUE, and dgNode::val.

00406 {
00407 struct dgNode *a;
00408 
00409 for (a=dg->nodeList; a != NULL; a = a->next)
00410     {
00411     if (!a->conn && a->val != NULL)
00412         break;
00413     }
00414 if (a == NULL)
00415     return NULL;
00416 rRefList = NULL;
00417 rMustHaveVal = TRUE;
00418 rFindConnected(a);
00419 return rRefList;
00420 }

Here is the call graph for this function:

struct dgNode* dgFindNode ( struct diGraph dg,
char *  name 
) [read]

Definition at line 100 of file diGraph.c.

References hashLookup(), diGraph::nodeHash, and hashEl::val.

Referenced by dgFindNumberedNode().

00102 {
00103 struct hashEl *hel;
00104 if ((hel = hashLookup(dg->nodeHash, name)) == NULL)
00105     return NULL;
00106 return hel->val;
00107 }

Here is the call graph for this function:

Here is the caller graph for this function:

struct dgConnection* dgFindNodeInConList ( struct dgConnection conList,
struct dgNode node 
) [read]

Definition at line 147 of file diGraph.c.

References dgConnection::next, and dgConnection::node.

Referenced by dgConnectWithVal(), dgDirectlyFollows(), and dgFindPath().

00149 {
00150 struct dgConnection *con;
00151 for (con = conList; con != NULL; con = con->next)
00152     if (con->node == node)
00153         return con;
00154 return NULL;
00155 }

Here is the caller graph for this function:

struct dgNodeRef* dgFindNodeInRefList ( struct dgNodeRef refList,
struct dgNode node 
) [read]

Definition at line 137 of file diGraph.c.

References dgNodeRef::next, and dgNodeRef::node.

00139 {
00140 struct dgNodeRef *ref;
00141 for (ref = refList; ref != NULL; ref = ref->next)
00142     if (ref->node == node)
00143         return ref;
00144 return NULL;
00145 }

struct dgNode* dgFindNumberedNode ( struct diGraph dg,
int  id 
) [read]

Definition at line 109 of file diGraph.c.

References dgFindNode().

00111 {
00112 char buf[16];
00113 sprintf(buf, "%d", id);
00114 return dgFindNode(dg, buf);
00115 }

Here is the call graph for this function:

struct dgNodeRef* dgFindPath ( struct diGraph dg,
struct dgNode a,
struct dgNode b 
) [read]

Definition at line 508 of file diGraph.c.

References AllocVar, dgFindNodeInConList(), dlAddValTail(), dlPopHead(), errAbort(), freeDlList(), freeMem(), newDlList(), dgConnection::next, dgNode::next, dgNode::nextList, dgConnection::node, diGraph::nodeList, slAddHead, slAddTail(), dgNode::tempEntry, and dlNode::val.

00510 {
00511 struct dgNodeRef *refList  = NULL, *ref;
00512 struct dgConnection *con;
00513 struct dgNode *node, *nNode;
00514 struct dlList *fifo;
00515 struct dlNode *ffNode;
00516 struct dgNode endNode;
00517 int fifoSize = 1;
00518 
00519 /* Do some quick and easy tests first to return if have no way out
00520  * of node A, or if B directly follows A. */
00521 if (a->nextList == NULL)
00522     return NULL;
00523 if (a == b)
00524     {
00525     AllocVar(ref);
00526     ref->node = a;
00527     return ref;
00528     }
00529 if ((con = dgFindNodeInConList(a->nextList, b)) != NULL)
00530     {
00531     AllocVar(refList);
00532     refList->node = a;
00533     node = con->node;
00534     AllocVar(ref);
00535     ref->node = node;
00536     slAddTail(&refList, ref);
00537     return refList;
00538     }
00539 
00540 /* Set up for breadth first traversal.  Will use a doubly linked
00541  * list as a fifo. */
00542 for (node = dg->nodeList; node != NULL; node = node->next)
00543     node->tempEntry = NULL;
00544 fifo = newDlList();
00545 dlAddValTail(fifo, a);
00546 a->tempEntry = &endNode;
00547 
00548 while ((ffNode = dlPopHead(fifo)) != NULL)
00549     {
00550     --fifoSize;
00551     node = ffNode->val;
00552     freeMem(ffNode);
00553     for (con = node->nextList; con != NULL; con = con->next)
00554         {
00555         nNode = con->node;
00556         if (nNode->tempEntry == NULL)
00557             {
00558             nNode->tempEntry = node;
00559             if (nNode == b)
00560                 {
00561                 while (nNode != &endNode && nNode != NULL)
00562                     {
00563                     AllocVar(ref);
00564                     ref->node = nNode;
00565                     slAddHead(&refList, ref);
00566                     nNode = nNode->tempEntry;
00567                     }
00568                 break;
00569                 }
00570             else
00571                 {
00572                 dlAddValTail(fifo, nNode);
00573                 ++fifoSize;
00574                 if (fifoSize > 100000)
00575                     errAbort("Internal error in dgFindPath");
00576                 }
00577             }
00578         }
00579     }
00580 freeDlList(&fifo);
00581 return refList;
00582 }

Here is the call graph for this function:

struct dgEdgeRef* dgFindSubEdges ( struct diGraph dg,
struct dgNodeRef subGraph 
) [read]

Definition at line 649 of file diGraph.c.

References AllocVar, dgConnection::edgeOnList, hashAdd(), hashLookup(), dgNode::name, newHash(), dgConnection::next, dgNodeRef::next, dgNode::nextList, dgConnection::node, dgNodeRef::node, slAddHead, and dlNode::val.

00651 {
00652 struct hash *hash = newHash(0);
00653 struct dgNodeRef *nr;
00654 struct dgConnection *con;
00655 struct dgEdgeRef *erList = NULL, *er;
00656 struct dgNode *node;
00657 
00658 /* Build up hash of nodes in subGraph. */
00659 for (nr = subGraph; nr != NULL; nr = nr->next)
00660     {
00661     node = nr->node;
00662     hashAdd(hash, node->name, node);
00663     }
00664 
00665 for (nr = subGraph; nr != NULL; nr = nr->next)
00666     {
00667     node = nr->node;
00668     for (con = node->nextList; con != NULL; con = con->next)
00669         {
00670         if (hashLookup(hash, con->node->name))
00671             {
00672             AllocVar(er);
00673             er->edge = con->edgeOnList->val;
00674             slAddHead(&erList, er);
00675             }
00676         }
00677     }
00678 freeHash(&hash);
00679 return erList;
00680 }

Here is the call graph for this function:

void dgFree ( struct diGraph **  pGraph  ) 

Definition at line 43 of file diGraph.c.

References dgNodeFreeList(), diGraph::edgeList, freeDlListAndVals(), freeHash(), freez(), diGraph::nodeHash, and diGraph::nodeList.

00045 {
00046 struct diGraph *dg = *pGraph;
00047 if (dg == NULL)
00048     return;
00049 freeHash(&dg->nodeHash);
00050 dgNodeFreeList(&dg->nodeList);
00051 freeDlListAndVals(&dg->edgeList);
00052 freez(pGraph);
00053 }

Here is the call graph for this function:

boolean dgHasCycles ( struct diGraph dg  ) 

Definition at line 341 of file diGraph.c.

References dgClearVisitFlags(), dgTopoSort(), FALSE, dgNode::next, diGraph::nodeList, rHasCycles(), TRUE, and dgNode::visited.

Referenced by dgConstrainedPriorityOrder().

00343 {
00344 struct dgNode *node;
00345 
00346 dgTopoSort(dg);
00347 dgClearVisitFlags(dg);
00348 for (node = dg->nodeList; node != NULL; node = node->next)
00349     {
00350     if (!node->visited)
00351         if (rHasCycles(node))
00352             return TRUE;
00353     }
00354 return FALSE;
00355 }

Here is the call graph for this function:

Here is the caller graph for this function:

struct diGraph* dgNew (  )  [read]

Definition at line 9 of file diGraph.c.

References AllocVar, diGraph::edgeList, newDlList(), newHash(), and diGraph::nodeHash.

00011 {
00012 struct diGraph *dg;
00013 AllocVar(dg);
00014 dg->nodeHash = newHash(0);
00015 dg->edgeList = newDlList();
00016 return dg;
00017 }

Here is the call graph for this function:

struct dgConnection* dgNextList ( struct dgNode node  )  [read]

Definition at line 710 of file diGraph.c.

References dgNode::nextList, and dgConnection::node.

00712 {
00713 return node->nextList;
00714 }

static void dgNodeFree ( struct dgNode **  pNode  )  [static]

Definition at line 19 of file diGraph.c.

References freez(), dgNode::nextList, dgNode::prevList, and slFreeList().

Referenced by dgNodeFreeList().

00021 {
00022 struct dgNode *node = *pNode;
00023 if (node == NULL)
00024     return;
00025 slFreeList(&node->nextList);
00026 slFreeList(&node->prevList);
00027 freez(pNode);
00028 }

Here is the call graph for this function:

Here is the caller graph for this function:

static void dgNodeFreeList ( struct dgNode **  pList  )  [static]

Definition at line 30 of file diGraph.c.

References dgNodeFree(), and dgNode::next.

Referenced by dgFree().

00032 {
00033 struct dgNode *el, *next;
00034 
00035 for (el = *pList; el != NULL; el = next)
00036     {
00037     next = el->next;
00038     dgNodeFree(&el);
00039     }
00040 *pList = NULL;
00041 }

Here is the call graph for this function:

Here is the caller graph for this function:

void* dgNodeName ( struct dgNode node  ) 

Definition at line 124 of file diGraph.c.

References dgNode::name.

00126 {
00127 return node->name;
00128 }

int dgNodeNumber ( struct dgNode node  ) 

Definition at line 130 of file diGraph.c.

References dgNode::name.

00133 {
00134 return atoi(node->name);
00135 }

void* dgNodeVal ( struct dgNode node  ) 

Definition at line 118 of file diGraph.c.

References dgNode::val.

00120 {
00121 return node->val;
00122 }

boolean dgParentsAllVisited ( struct dgNode node  ) 

Definition at line 592 of file diGraph.c.

References FALSE, dgConnection::next, dgConnection::node, dgNode::prevList, TRUE, and dgNode::visited.

Referenced by dgConstrainedPriorityOrder().

00594 {
00595 struct dgConnection *con;
00596 for (con = node->prevList; con != NULL; con = con->next)
00597     {
00598     if (con->node->visited == FALSE)
00599         return FALSE;
00600     }
00601 return TRUE;
00602 }

Here is the caller graph for this function:

boolean dgPathExists ( struct diGraph dg,
struct dgNode a,
struct dgNode b 
)

Definition at line 285 of file diGraph.c.

References dgClearVisitFlags(), rPathExists(), and rTarget.

00287 {
00288 rTarget = b;
00289 dgClearVisitFlags(dg);
00290 return rPathExists(a);
00291 }

Here is the call graph for this function:

struct dgConnection* dgPrevList ( struct dgNode node  )  [read]

Definition at line 716 of file diGraph.c.

References dgConnection::node, and dgNode::prevList.

00718 {
00719 return node->prevList;
00720 }

static struct dlNode* dgRemoveFromConList ( struct dgConnection **  pConList,
struct dgNode node,
struct dgConnection **  retCon 
) [static, read]

Definition at line 204 of file diGraph.c.

References dgConnection::edgeOnList, freeMem(), dlNode::next, dgConnection::next, dgConnection::node, and slAddHead.

Referenced by dgDisconnect(), and dgSwapEdges().

00207 {
00208 struct dgConnection *newList = NULL;
00209 struct dgConnection *con, *next;
00210 struct dlNode *edgeOnList = NULL;
00211 
00212 for (con = *pConList; con != NULL; con = next)
00213     {
00214     next = con->next;
00215     if (con->node == node)
00216         {
00217         edgeOnList = con->edgeOnList;
00218         if (retCon != NULL)
00219             *retCon = con;
00220         else
00221             freeMem(con);
00222         }
00223     else
00224         {
00225         slAddHead(&newList, con);
00226         }
00227     }
00228 slReverse(&newList);
00229 *pConList = newList;
00230 return edgeOnList;
00231 }

Here is the call graph for this function:

Here is the caller graph for this function:

void dgSwapEdges ( struct diGraph dg,
struct dgEdgeRef erList 
)

Definition at line 682 of file diGraph.c.

References dgEdge::a, dgEdge::b, dgRemoveFromConList(), dgEdgeRef::edge, dgEdgeRef::next, dgNode::nextList, dgConnection::node, dgNode::prevList, and slAddHead.

00685 {
00686 struct dgEdgeRef *er;
00687 struct dgEdge *edge;
00688 struct dgNode *a, *b;
00689 struct dgConnection *con1, *con2;
00690 
00691 /* Remove edges from next and previous list of all
00692  * involved nodes and swap nodes in edge itself. */
00693 for (er = erList; er != NULL; er = er->next)
00694     {
00695     edge = er->edge;
00696     a = edge->a;
00697     b = edge->b;
00698     dgRemoveFromConList(&a->nextList, b, &con1);
00699     dgRemoveFromConList(&b->prevList, a, &con2);
00700     edge->a = b;
00701     edge->b = a;
00702     con1->node = a;
00703     slAddHead(&b->nextList, con1);
00704     con2->node = b;
00705     slAddHead(&a->prevList, con2);
00706     }
00707 }

Here is the call graph for this function:

void dgTopoSort ( struct diGraph dg  ) 

Definition at line 307 of file diGraph.c.

References dgClearVisitFlags(), dgNode::next, diGraph::nodeList, rTopoSort(), topoIx, and dgNode::visited.

Referenced by dgHasCycles().

00309 {
00310 struct dgNode *node;
00311 
00312 topoIx = 0;
00313 dgClearVisitFlags(dg);
00314 for (node = dg->nodeList; node != NULL; node = node->next)
00315     {
00316     if (!node->visited)
00317         rTopoSort(node);
00318     }
00319 }

Here is the call graph for this function:

Here is the caller graph for this function:

static void rFindConnected ( struct dgNode a  )  [static]

Definition at line 361 of file diGraph.c.

References AllocVar, dgNode::conn, dgConnection::next, dgNode::nextList, dgConnection::node, dgNodeRef::node, dgNode::prevList, rMustHaveVal, rRefList, slAddHead, TRUE, and dgNode::val.

Referenced by connectedComponents(), dgFindNewConnected(), dgFindNewConnectedWithVals(), dgFindNextConnected(), and dgFindNextConnectedWithVals().

00364 {
00365 if (!a->conn && (!rMustHaveVal || a->val))
00366     {
00367     struct dgNodeRef *ref;
00368     struct dgConnection *con;
00369     AllocVar(ref);
00370     ref->node = a;
00371     slAddHead(&rRefList, ref);
00372     a->conn = TRUE;
00373     for (con = a->nextList; con != NULL; con = con->next)
00374         rFindConnected(con->node);
00375     for (con = a->prevList; con != NULL; con = con->next)
00376         rFindConnected(con->node);
00377     }
00378 }

Here is the caller graph for this function:

static boolean rHasCycles ( struct dgNode node  )  [static]

Definition at line 321 of file diGraph.c.

References FALSE, dgConnection::next, dgNode::nextList, dgConnection::node, dgNode::topoOrder, TRUE, and dgNode::visited.

Referenced by dgHasCycles().

00324 {
00325 struct dgConnection *ref;
00326 struct dgNode *child;
00327 
00328 node->visited = TRUE;
00329 for (ref = node->nextList; ref != NULL; ref = ref->next)
00330     {
00331     child = ref->node;
00332     if (child->topoOrder > node->topoOrder)
00333         return TRUE;
00334     if (!child->visited)
00335         if (rHasCycles(child))
00336             return TRUE;
00337     }
00338 return FALSE;
00339 }

Here is the caller graph for this function:

static boolean rPathExists ( struct dgNode a  )  [static]

Definition at line 269 of file diGraph.c.

References FALSE, dgConnection::next, dgNode::nextList, dgConnection::node, rTarget, TRUE, and dgNode::visited.

Referenced by dgPathExists().

00271 {
00272 struct dgConnection *ref;
00273 if (a == rTarget)
00274     return TRUE;
00275 a->visited = TRUE;
00276 
00277 for (ref = a->nextList; ref != NULL; ref = ref->next)
00278     {
00279     if (!ref->node->visited && rPathExists(ref->node))
00280         return TRUE;
00281     }
00282 return FALSE;
00283 }

Here is the caller graph for this function:

static void rTopoSort ( struct dgNode node  )  [static]

Definition at line 295 of file diGraph.c.

References dgConnection::next, dgNode::nextList, dgConnection::node, topoIx, dgNode::topoOrder, TRUE, and dgNode::visited.

Referenced by dgTopoSort().

00296 {
00297 struct dgConnection *ref;
00298 node->visited = TRUE;
00299 for (ref = node->nextList; ref != NULL; ref = ref->next)
00300     {
00301     if (!ref->node->visited)
00302         rTopoSort(ref->node);
00303     }
00304 node->topoOrder = ++topoIx;
00305 }

Here is the caller graph for this function:


Variable Documentation

char const rcsid[] = "$Id: diGraph.c,v 1.9 2005/08/17 03:01:29 galt Exp $" [static]

Definition at line 7 of file diGraph.c.

bool rMustHaveVal

Definition at line 358 of file diGraph.c.

Referenced by connectedComponents(), dgConnectedComponents(), dgConnectedComponentsWithVals(), dgFindNewConnected(), dgFindNewConnectedWithVals(), dgFindNextConnected(), dgFindNextConnectedWithVals(), and rFindConnected().

struct dgNodeRef* rRefList

Definition at line 357 of file diGraph.c.

Referenced by connectedComponents(), dgFindNewConnected(), dgFindNewConnectedWithVals(), dgFindNextConnected(), dgFindNextConnectedWithVals(), and rFindConnected().

struct dgNode* rTarget [static]

Definition at line 267 of file diGraph.c.

Referenced by dgPathExists(), and rPathExists().

int topoIx [static]

Definition at line 293 of file diGraph.c.

Referenced by dgTopoSort(), and rTopoSort().


Generated on Tue Dec 25 19:43:31 2007 for blat by  doxygen 1.5.2