static int dfs_main(Graph * graph, AdjList * adjlist, List * ordered)
{

	AdjList *clr_adjlist;

	DfsVertex *clr_vertex, *adj_vertex;

	ListElmt *member;

/*****************************************************************************
*  Color the vertex gray and traverse its adjacency list.                    *
*****************************************************************************/

	((DfsVertex *) adjlist->vertex)->color = gray;

	for (member = list_head(&adjlist->adjacent); member != NULL; member =
	     list_next(member)) {

   /**************************************************************************
   *  Determine the color of the next adjacent vertex.                       *
   **************************************************************************/

		adj_vertex = list_data(member);

		if (graph_adjlist(graph, adj_vertex, &clr_adjlist) != 0)
			return -1;

		clr_vertex = clr_adjlist->vertex;

   /**************************************************************************
   *  Move one vertex deeper when the next adjacent vertex is white.         *
   **************************************************************************/

		if (clr_vertex->color == white) {

			if (dfs_main(graph, clr_adjlist, ordered) != 0)
				return -1;

		}

	}

/*****************************************************************************
*  Color the current vertex black and make it first in the list.             *
*****************************************************************************/

	((DfsVertex *) adjlist->vertex)->color = black;

	if (list_ins_next(ordered, NULL, (DfsVertex *) adjlist->vertex) != 0)
		return -1;

	return 0;

}
Example #2
0
int bfs(Graph *graph, BfsVertex *start, List *hops) {

Queue              queue;

AdjList            *adjlist,
                   *clr_adjlist;

BfsVertex          *clr_vertex,
                   *adj_vertex;

ListElmt           *element,
                   *member;

/*****************************************************************************
*                                                                            *
*  Initialize all of the vertices in the graph.                              *
*                                                                            *
*****************************************************************************/

for (element = list_head(&graph_adjlists(graph)); element != NULL; element =
   list_next(element)) {

   clr_vertex = ((AdjList *)list_data(element))->vertex;

   if (graph->match(clr_vertex, start)) {

      /***********************************************************************
      *                                                                      *
      *  Initialize the start vertex.                                        *
      *                                                                      *
      ***********************************************************************/

      clr_vertex->color = gray;
      clr_vertex->hops = 0;

      }

   else {

      /***********************************************************************
      *                                                                      *
      *  Initialize vertices other than the start vertex.                    *
      *                                                                      *
      ***********************************************************************/

      clr_vertex->color = white;
      clr_vertex->hops = -1;

   }

}

/*****************************************************************************
*                                                                            *
*  Initialize the queue with the adjacency list of the start vertex.         *
*                                                                            *
*****************************************************************************/

queue_init(&queue, NULL);

if (graph_adjlist(graph, start, &clr_adjlist) != 0) {

   queue_destroy(&queue);
   return -1;

}

if (queue_enqueue(&queue, clr_adjlist) != 0) {

   queue_destroy(&queue);
   return -1;

}

/*****************************************************************************
*                                                                            *
*  Perform breadth-first search.                                             *
*                                                                            *
*****************************************************************************/

while (queue_size(&queue) > 0) {

   adjlist = queue_peek(&queue);

   /**************************************************************************
   *                                                                         *
   *  Traverse each vertex in the current adjacency list.                    *
   *                                                                         *
   **************************************************************************/

   for (member = list_head(&adjlist->adjacent); member != NULL; member =
      list_next(member)) {

      adj_vertex = list_data(member);

      /***********************************************************************
      *                                                                      *
      *  Determine the color of the next adjacent vertex.                    *
      *                                                                      *
      ***********************************************************************/

      if (graph_adjlist(graph, adj_vertex, &clr_adjlist) != 0) {

         queue_destroy(&queue);
         return -1;

      }

      clr_vertex = clr_adjlist->vertex;

      /***********************************************************************
      *                                                                      *
      *  Color each white vertex gray and enqueue its adjacency list.        *
      *                                                                      *
      ***********************************************************************/

      if (clr_vertex->color == white) {

         clr_vertex->color = gray;
         clr_vertex->hops = ((BfsVertex *)adjlist->vertex)->hops + 1;

         if (queue_enqueue(&queue, clr_adjlist) != 0) {

            queue_destroy(&queue);
            return -1;

         }

      }

   }

   /**************************************************************************
   *                                                                         *
   *  Dequeue the current adjacency list and color its vertex black.         *
   *                                                                         *
   **************************************************************************/

   if (queue_dequeue(&queue, (void **)&adjlist) == 0) {

      ((BfsVertex *)adjlist->vertex)->color = black;

      }

   else {

      queue_destroy(&queue);
      return -1;

   }

}

queue_destroy(&queue);

/*****************************************************************************
*                                                                            *
*  Pass back the hop count for each vertex in a list.                        *
*                                                                            *
*****************************************************************************/

list_init(hops, NULL);

for (element = list_head(&graph_adjlists(graph)); element != NULL; element =
   list_next(element)) {

   /**************************************************************************
   *                                                                         *
   *  Skip vertices that were not visited (those with hop counts of -1).     *
   *                                                                         *
   **************************************************************************/

   clr_vertex = ((AdjList *)list_data(element))->vertex;

   if (clr_vertex->hops != -1) {

      if (list_ins_next(hops, list_tail(hops), clr_vertex) != 0) {

         list_destroy(hops);
         return -1;

      }

   }

}

return 0;

}
Example #3
0
int main(int argc, char **argv) {

Graph              graph;

AdjList            *adjlist;

ListElmt           *element;

char               *data,
                   data1[STRSIZ],
                   *data2;

int                retval,
                   size,
                   i;

/*****************************************************************************
*                                                                            *
*  Initialize the graph.                                                     *
*                                                                            *
*****************************************************************************/

graph_init(&graph, match_str, free);

/*****************************************************************************
*                                                                            *
*  Perform some graph operations.                                            *
*                                                                            *
*****************************************************************************/

if ((data = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data, "a");
fprintf(stdout, "Inserting vertex %s\n", data);

if (graph_ins_vertex(&graph, data) != 0)
   return 1;

if ((data = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data, "b");
fprintf(stdout, "Inserting vertex %s\n", data);

if (graph_ins_vertex(&graph, data) != 0)
   return 1;

if ((data = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data, "c");
fprintf(stdout, "Inserting vertex %s\n", data);

if (graph_ins_vertex(&graph, data) != 0)
   return 1;

if ((data = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data, "d");
fprintf(stdout, "Inserting vertex %s\n", data);

if (graph_ins_vertex(&graph, data) != 0)
   return 1;

if ((data = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data, "e");
fprintf(stdout, "Inserting vertex %s\n", data);

if (graph_ins_vertex(&graph, data) != 0)
   return 1;

print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data1, "a");
strcpy(data2, "b");
fprintf(stdout, "Inserting edge %s to %s\n", data1, data2);

if (graph_ins_edge(&graph, data1, data2) != 0)
   return 1;

print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data1, "a");
strcpy(data2, "c");
fprintf(stdout, "Inserting edge %s to %s\n", data1, data2);

if (graph_ins_edge(&graph, data1, data2) != 0)
   return 1;

print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data1, "b");
strcpy(data2, "c");
fprintf(stdout, "Inserting edge %s to %s\n", data1, data2);

if (graph_ins_edge(&graph, data1, data2) != 0)
   return 1;

print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data1, "b");
strcpy(data2, "d");
fprintf(stdout, "Inserting edge %s to %s\n", data1, data2);

if (graph_ins_edge(&graph, data1, data2) != 0)
   return 1;

print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data1, "c");
strcpy(data2, "b");
fprintf(stdout, "Inserting edge %s to %s\n", data1, data2);

if (graph_ins_edge(&graph, data1, data2) != 0)
   return 1;

print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data1, "c");
strcpy(data2, "c");
fprintf(stdout, "Inserting edge %s to %s\n", data1, data2);

if (graph_ins_edge(&graph, data1, data2) != 0)
   return 1;

print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data1, "c");
strcpy(data2, "d");
fprintf(stdout, "Inserting edge %s to %s\n", data1, data2);

if (graph_ins_edge(&graph, data1, data2) != 0)
   return 1;

print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data1, "d");
strcpy(data2, "a");
fprintf(stdout, "Inserting edge %s to %s\n", data1, data2);

if (graph_ins_edge(&graph, data1, data2) != 0)
   return 1;

print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data1, "e");
strcpy(data2, "c");
fprintf(stdout, "Inserting edge %s to %s\n", data1, data2);

if (graph_ins_edge(&graph, data1, data2) != 0)
   return 1;

print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data1, "e");
strcpy(data2, "d");
fprintf(stdout, "Inserting edge %s to %s\n", data1, data2);

if (graph_ins_edge(&graph, data1, data2) != 0)
   return 1;

print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data1, "a");
strcpy(data2, "c");
data = data2;

fprintf(stdout, "Removing edge %s to %s\n", data1, data2);

if (graph_rem_edge(&graph, data1, (void **)&data) != 0)
   return 1;

free(data);
print_graph(&graph);

strcpy(data1, "c");
strcpy(data2, "c");
data = data2;

fprintf(stdout, "Removing edge %s to %s\n", data1, data2);

if (graph_rem_edge(&graph, data1, (void **)&data) != 0)
   return 1;

free(data);
print_graph(&graph);

strcpy(data1, "e");
strcpy(data2, "c");
data = data2;

fprintf(stdout, "Removing edge %s to %s\n", data1, data2);

if (graph_rem_edge(&graph, data1, (void **)&data) != 0)
   return 1;

free(data);
print_graph(&graph);

strcpy(data1, "a");
strcpy(data2, "b");
data = data2;

fprintf(stdout, "Removing edge %s to %s\n", data1, data2);

if (graph_rem_edge(&graph, data1, (void **)&data) != 0)
   return 1;

free(data);
print_graph(&graph);

strcpy(data1, "d");
strcpy(data2, "a");
data = data2;

fprintf(stdout, "Removing edge %s to %s\n", data1, data2);

if (graph_rem_edge(&graph, data1, (void **)&data) != 0)
   return 1;

free(data);
print_graph(&graph);

free(data2);

strcpy(data1, "a");
data = data1;

fprintf(stdout, "Removing vertex %s\n", data1);

if (graph_rem_vertex(&graph, (void **)&data) != 0)
   return 1;

free(data);
print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data1, "f");
strcpy(data2, "a");

retval = graph_ins_edge(&graph, data1, data2);
fprintf(stdout,"Inserting an invalid edge from %s to %s...Value=%d (-1=OK)\n",
   data1, data2, retval);

if (retval != 0)
   free(data2);

print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data1, "c");
strcpy(data2, "b");

retval = graph_ins_edge(&graph, data1, data2);
fprintf(stdout,"Inserting an existing edge from %s to %s...Value=%d (1=OK)\n",
   data1, data2, retval);

if (retval != 0)
   free(data2);

print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data1, "f");
strcpy(data2, "a");
data = data2;

retval = graph_rem_edge(&graph, data1, (void **)&data);
fprintf(stdout, "Removing an invalid edge from %s to %s...Value=%d (-1=OK)\n",
   data1, data2, retval);

if (retval == 0)
   free(data);

free(data2);
print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data1, "c");
strcpy(data2, "e");
data = data2;

retval = graph_rem_edge(&graph, data1, (void **)&data);
fprintf(stdout, "Removing an invalid edge from %s to %s...Value=%d (-1=OK)\n",
   data1, data2, retval);

if (retval == 0)
   free(data);

free(data2);
print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data2, "c");

retval = graph_ins_vertex(&graph, data2);
fprintf(stdout, "Inserting an existing vertex %s...Value=%d (1=OK)\n", data1,
   retval);

if (retval != 0)
   free(data2);

print_graph(&graph);

if ((data2 = (char *)malloc(STRSIZ)) == NULL)
   return 1;

strcpy(data1, "b");
strcpy(data2, "d");

retval = graph_is_adjacent(&graph, data1, data2);
fprintf(stdout, "Testing graph_is_adjacent (%s, %s)...Value=%d (1=OK)\n",
   data1, data2, retval);

strcpy(data1, "a");
strcpy(data2, "e");

retval = graph_is_adjacent(&graph, data1, data2);
fprintf(stdout, "Testing graph_is_adjacent (%s, %s)...Value=%d (0=OK)\n",
   data1, data2, retval);

strcpy(data1, "e");
strcpy(data2, "d");

retval = graph_is_adjacent(&graph, data1, data2);
fprintf(stdout, "Testing graph_is_adjacent (%s, %s)...Value=%d (1=OK)\n",
   data1, data2, retval);

strcpy(data1, "c");
strcpy(data2, "a");

retval = graph_is_adjacent(&graph, data1, data2);
fprintf(stdout, "Testing graph_is_adjacent (%s, %s)...Value=%d (0=OK)\n",
   data1, data2, retval);

free(data2);

strcpy(data1, "c");

if (graph_adjlist(&graph, data1, &adjlist) != 0)
   return 1;

fprintf(stdout, "Vertices adjacent to %s: ", data1);

i = 0;
size = set_size(&adjlist->adjacent);
element = list_head(&adjlist->adjacent);

while (i < size) {

   i++;
   if (i > 1) fprintf(stdout, ", ");
   fprintf(stdout, "%s", (char *)list_data(element));
   element = list_next(element);

}

fprintf(stdout, "\n");

/*****************************************************************************
*                                                                            *
*  Destroy the graph.                                                        *
*                                                                            *
*****************************************************************************/

fprintf(stdout, "Destroying the graph\n");
graph_destroy(&graph);

return 0;

}