#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <malloc.h>
#include <assert.h>
#include "slist.h"
#include "set.h"
#include "utils.h"
Go to the source code of this file.
Typedefs | |
typedef enum VertexColor_ | VertexColor |
typedef struct Vertex_ * | Vertex |
typedef struct Graph_ * | Graph |
typedef SlistNode | VertexNode |
typedef SlistNode | EdgeNode |
Enumerations | |
enum | VertexColor_ { white, gray, black } |
Functions | |
Graph | GRAPHinit (int(*match)(const void *key1, const void *key2), void(*destroy)(void *data)) |
void | GRAPHdestroy (Graph graph) |
int | GRAPHinsvertex (Graph graph, const void *vtxdata) |
int | GRAPHinsedge (Graph graph, const void *vtxdata, const void *adjdata) |
int | GRAPHremvertex (Graph graph, void **vtxdata) |
int | GRAPHremedge (Graph graph, void *vtxdata, void **edgedata) |
VertexNode | GRAPHgetvertexhead (Graph graph) |
EdgeNode | GRAPHgetedgehead (VertexNode vtxnode) |
VertexNode | GRAPHgetvertexnext (VertexNode vtxnode) |
EdgeNode | GRAPHgetedgenext (EdgeNode enode) |
void * | GRAPHgetvertexdata (VertexNode vtxnode) |
void * | GRAPHgetedgedata (EdgeNode enode) |
int | GRAPHgetedgecount (VertexNode vtxnode) |
int | GRAPHvcount (Graph graph) |
int | GRAPHecount (Graph graph) |
void | GRAPHprint (Graph graph, void(*vtxcallback)(const void *data), void(*edgecallback)(const void *data)) |
void | GRAPHtraverse (Graph graph, void(*vtxcallback)(const void *data), void(*edgecallback)(const void *data)) |
VertexNode | GRAPHfindvertex (const Graph graph, const void *vtxdata) |
EdgeNode | GRAPHfindedge (const Graph graph, const void *vtxdata, const void *edgedata) |
int | GRAPHis_adjacent (const Graph graph, const void *vtxdata, const void *edgedata) |
int | GRAPHis_isolated (const Graph graph, const void *vtxdata) |
typedef enum VertexColor_ VertexColor |
Define colors for vertices in graphs
enum VertexColor_ |
void GRAPHdestroy | ( | Graph | graph | ) |
Destroy the graph
The graph is destroyed - that is, all the memory occupied by the vertices and edges is deallocated. The user-defined callback function destroy, given as an argument to GRAPHinit(), is responsible for freeing dynamically allocated vertex/edge data, when this function is called. When all vertices/edges and corresponding data have been deallocated - the graph header is deallocated, too.
[in] | graph | - a reference to current graph. |
int GRAPHecount | ( | Graph | graph | ) |
Find edge - incident from vertex specified by vtxdata - and also incident to vertex specfied by edgedata
Search the graph for an edge, whose data matches search key data referenced by parameter edgedata. Moreover, this data should be found in a node, present in the adjacency list of a vertex, matching data referenced by parameter vtxdata. Thus, if an edge exists, incident from vertex specified by vtxdata - and also incident to vertex specified by edgedata - then a node must exist in the adjacency list of vertex specified by vtxdata, that is matching edgedata. In other words, parameter edgedata specifies the vertex, which the target edge is incident to. This is how edges are implemented in our graph. A reference to the node with a match will be returned - NULL otherwise. A user-defined callback function, responsible for doing the matching of node data - with data referenced by parameter data - must exist for this function to work - otherwise NULL will be returned - always. This user-supplied match-callback is set into the graph when it was created, with a call to function - GRAPHinit().
[in] | graph | - a reference to current graph. |
[in] | vtxdata | - reference to search key data for the vertex node, which the target edge is incident from. |
[in] | edgedata | - reference to search key data for the (edge) node - situated in the adjacency list of vertex node specified by parameter vtxdata |
VertexNode GRAPHfindvertex | ( | const Graph | graph, |
const void * | vtxdata | ||
) |
Find vertex node containing data referenced by vtxdata
Search the graph for a vertex, whose data matches the search key data referenced by parameter vtxdata. A reference to the vertex with a match will be returned - NULL otherwise. A user-defined callback function, responsible for doing the matching of vertex data - with data referenced by parameter vtxdata - must exist for this function to work - otherwise NULL will be returned - always. This user-supplied match-callback was set into the graph when it was created, with a call to function - GRAPHinit().
[in] | graph | - a reference to current graph |
[in] | vtxdata | - a reference to search key data for the vertex to be found |
int GRAPHgetedgecount | ( | VertexNode | vtxnode | ) |
Get number of edges incident from a vertex
Alternate desription: Get the number of nodes in the adjacency list of the vertex node vtxdata.
[in] | vtxnode | - a reference to a valid vertex node in the graph. |
void* GRAPHgetedgedata | ( | EdgeNode | enode | ) |
EdgeNode GRAPHgetedgehead | ( | VertexNode | vtxnode | ) |
void* GRAPHgetvertexdata | ( | VertexNode | vtxnode | ) |
VertexNode GRAPHgetvertexhead | ( | Graph | graph | ) |
VertexNode GRAPHgetvertexnext | ( | VertexNode | vtxnode | ) |
Graph GRAPHinit | ( | int(*)(const void *key1, const void *key2) | match, |
void(*)(void *data) | destroy | ||
) |
Initialize the graph
This function simply sets up the graph so that it can be used in forthcoming operations, i.e. internal counters are set to 0, and the call-backs given as parameters are encapsulated within the graph structure.
[in] | match | - a reference to a user-defined function that receives references to vertex key data - and search key data - via its parameters key1 and key2. Hence this callback function can make the actual matching of search key and vertex key data - and determine if search data is present in the graph. This callback function shall return 1 - in case of a hit - or 0 otherwise. |
[in] | destroy | - A reference to a user-defined function, reponsible for freeing vertex and edge data, when the graph is deleted. If destroy is NULL - then vertex and edge data will be left untouched when the graph is destroyed. |
int GRAPHinsedge | ( | Graph | graph, |
const void * | vtxdata, | ||
const void * | adjdata | ||
) |
Insert an edge, incident from vertex specified by vtxdata - and also incident to vertex specified by adjdata.
Both vertices making up the edge must, of course, already exist in the graph, that is, have been inserted previously by a call to GRAPHinsvertex(). The newly inserted edge is represented by a node, with a reference to adjdata, in the adjacency(=edge) list of the vertex specified by vtxdata. The memory referenced by adjdata should remain valid as long as the edge remains in the graph. This memory is also where you normally put edge data specifics - such as cost, distance, etc. It's the responsibility of the caller to manage the storage referenced by adjdata. To model an edge (u,v) in an undirected graph, you should call this interface function twice: First time to insert an edge from u to v - and again to insert an edge in the opposite direction - from v to u. Thus, in undirected graphs, you have to do 2 edge insertions for each (undirected) edge.
[in] | graph | - a reference to current graph. |
[in] | vtxdata | - a reference to search (key) data of the vertex, which the edge is incident from. |
[in] | adjdata | - a reference to data of the vertex, which the edge is incident to. This referenced data memory must remain valid as long as the edge remains in the graph - and it is the responsibility of the caller to handle it from now on. |
int GRAPHinsvertex | ( | Graph | graph, |
const void * | vtxdata | ||
) |
Insert a vertex into the graph
The new vertex node inserted will contain a pointer to vtxdata, so the memory referenced by vtxdata must be valid as long as the vertex is part of the graph. It's the responsibility of the caller to manage this memory - referenced by vtxdata.
[in] | graph | - a reference to current graph. |
[in] | vtxdata | - reference to data of vertex to be inserted. |
int GRAPHis_adjacent | ( | const Graph | graph, |
const void * | vtxdata, | ||
const void * | edgedata | ||
) |
Determine if 2 vertices are adjacent - i.e. if there is an edge connecting them
More in detail, this function determines if there is an edge - incident from vertex matching search key data referenced by parameter vtxdata - which is incident to another vertex, matching search key data referenced by parameter edgedata. Or - equivalently put - if vertex matching search key data referenced by edgedata is present in the adjacency list of vertex specified by parameter vtxdata.
[in] | graph | - a reference to current graph. |
[in] | vtxdata | - reference to search key data for vertex, which the edge is incident from. |
[in] | edgedata | - reference to search key data for vertex, which the edge is incident to. |
int GRAPHis_isolated | ( | const Graph | graph, |
const void * | vtxdata | ||
) |
Determine if a vertex is isolated - i.e. has no (in- or outgoing) edges
If a vertex is to be considered isolated - the following must be true:
[in] | graph | - a reference to current graph. |
[in] | vtxdata | - reference to search key data for target vertex. |
void GRAPHprint | ( | Graph | graph, |
void(*)(const void *data) | vtxcallback, | ||
void(*)(const void *data) | edgecallback | ||
) |
Print all vertex and edge data of the graph - on screen
[in] | graph | - a reference to current graph. |
[in] | vtxcallback | - reference to user-defined callback function, that gets read access to vertex data via its parameter vtxcallback - to do whatever is relevant. In this case it is a matter of formatting vertex data for printing on screen. The printed data should be kept to a minimum (the key value, for example) in order not to clutter the screen. This function is primarily for small graphs and debugging purposes |
[in] | edgecallback | - reference to user-defined callback function, that gets read access to edge data via its parameter edgecallback - to do whatever is relevant. In this case it is a matter of formatting edge data for printing on screen. The printed data should be kept to a minimum (the key value, for example) in order not to clutter the screen. This function is primarily for small graphs and debugging purposes |
int GRAPHremedge | ( | Graph | graph, |
void * | vtxdata, | ||
void ** | edgedata | ||
) |
Remove edge - incident from vertex specified by vtxdata - and also incident to vertex spec. by edgedata
When called, the 3rd parameter of this function, edgedata, should reference an (external) pointer, that points to edge search (key) data. After the call - this pointer referenced by parameter edgedata, has been redirected to point to data part of the removed (edge) node - if the call was succesful. The caller is responsible for the future of this memory - deallocating it, if needed, for example. This removed edge data will typically contain:
[in] | graph | - a reference to current graph. |
[in] | vtxdata | - a reference to vertex search (key) data of the vertex, which the target edge is incident from.. |
[in,out] | edgedata | - a reference to an external pointer, initially pointing to edge search (key) data. After the call, the external pointer is redirected to reference removed edge data - i.e. search key data for the vertex, which the edge is incident to. |
int GRAPHremvertex | ( | Graph | graph, |
void ** | vtxdata | ||
) |
Removal of vertex - with data referenced by vtxdata
When called, the 2nd parameter of this function, vtxdata, should reference a pointer, that points to search (key)data. After the call - this (external) data pointer referenced by parameter vtxdata, has been redirected to point to data of the removed node - if the call was succesful. The caller is responsible for the future of this memory - deallocating it, if needed, for example.
For successful removal there are 2 preconditions to be met by the target vertex. The vertex to be removed must be isolated - which implies the following:
Under these circumstances, the vertex specified with parameter vtxdata is isolated (edge-free). Now it can be removed - and accessed by the redirected, external pointer, that was manipulated by parameter vtxdata.
[in] | graph | - a reference to current graph. |
[in,out] | vtxdata | - reference to (external) pointer, that prior to call should point to vertex search (key) data. After the call, this external pointer is redirected to reference removed vertex data. |
void GRAPHtraverse | ( | Graph | graph, |
void(*)(const void *data) | vtxcallback, | ||
void(*)(const void *data) | edgecallback | ||
) |
Traverse all vertices/edges of the graph
[in] | graph | - a reference to current graph. |
[in] | vtxcallback | - reference to user-defined callback function, that gets read access to vertex data via its parameter vtxcallback - to do whatever is relevant. |
[in] | edgecallback | - reference to user-defined callback function, that gets read access to edge data via its parameter edgecallback - to do whatever is relevant. |