Example #1
0
void constructGraph(int internalDegree, int depth){
    int i, j, k;
    int minLeaf, maxLeaf;
    
    GRAPH graph;
    ADJACENCY adj;
    
    prepareGraph(graph, adj, getOrder(internalDegree, depth));
    
    if(depth==0){
        writeMultiCode(graph, adj, stdout);
        return;
    }
    
    for(i = 0; i < internalDegree; i++){
        addEdge(graph, adj, 1, 2 + i);
    }
    
    minLeaf = 2;
    maxLeaf = 1 + internalDegree;
    
    for(i = 1; i < depth; i++){
        int newLeaf = maxLeaf + 1;
        for(j = minLeaf; j <= maxLeaf; j++){
            for(k = 0; k < internalDegree - 1; k++){
                addEdge(graph, adj, j, newLeaf);
                newLeaf++;
            }
        }
        minLeaf = maxLeaf + 1;
        maxLeaf = newLeaf - 1;
    }
    
    writeMultiCode(graph, adj, stdout);
}
void handleBiconnectedComponent(GRAPH graph, ADJACENCY adj, int uEnd, int vEnd){
    int i, u, v;
    GRAPH biconnectedGraph;
    ADJACENCY biconnectedAdj;
    int newLabel[MAXN+1];
    
    for(i = 0; i < MAXN; i++){
        newLabel[i] = 0;
    }
    
    //we will use i to relabel the vertices
    i = 0;
    
    //just prepare the graph for a large enough number of vertices
    prepareGraph(biconnectedGraph, biconnectedAdj, graph[0][0]);
    
    do {
        POP_EDGE(u,v);
        if(!newLabel[u]){
            i++;
            newLabel[u] = i;
        }
        if(!newLabel[v]){
            i++;
            newLabel[v] = i;
        }
        //no extra check needed since each edge is only once in the stack
        addEdge(biconnectedGraph, biconnectedAdj, newLabel[u], newLabel[v]);
    } while(uEnd != u || vEnd != v);
    
    //set the connect number of vertices
    biconnectedGraph[0][0] = i;
    
    writeMultiCode(biconnectedGraph, biconnectedAdj, stdout);
}
Example #3
0
/*
 * Constructs the cycle graph with the specified number of vertices.
 * The graph is output in multi_code format.
 */
void constructGraph(int order){
    int i;
    
    GRAPH graph;
    ADJACENCY adj;
    
    prepareGraph(graph, adj, order);
    
    for(i = 1; i <= order; i++){
        addEdge(graph, adj, i, (i%order)+1);
    }
    
    writeMultiCode(graph, adj, stdout);
}
Example #4
0
void codetograph(char *code, GRAPH graph, ADJACENCY adj) {
    char i, v = 1, w;
    
    prepareGraph(graph, adj, n);

    for (i = n * k / 2; i > 0; i--) {
        w = *code;
        while (adj[v] == k) {
            v++;
        }
        addEdge(graph, adj, v, w);
        code++;
    }
}
Example #5
0
void constructCorona(GRAPH graph, ADJACENCY adj, GRAPH coronaGraph, ADJACENCY coronaAdj){
    int i, j;
    
    int order = graph[0][0];
    
    prepareGraph(coronaGraph, coronaAdj, order*2);
    
    for(i=1; i<=order; i++){
        for(j=0; j<adj[i]; j++){
            if(i < graph[i][j]){
                addEdge(coronaGraph, coronaAdj, i, graph[i][j]);
            }
        }
        addEdge(coronaGraph, coronaAdj, i, i + order);
    }
}
Example #6
0
/*
 * Constructs the generalized Petersengraph G(n,k).
 * The graph is output in multi_code format.
 */
void constructGraph(int n, int k){
    int i;
    
    GRAPH graph;
    ADJACENCY adj;
    
    prepareGraph(graph, adj, 2*n);
    
    for(i = 1; i <= n; i++){
        addEdge(graph, adj, i, (i%n)+1);
        addEdge(graph, adj, i, i + n);
        addEdge(graph, adj, i+n, ((i-1+k)%n) + n + 1);
    }
    
    writeMultiCode(graph, adj, stdout);
}
Example #7
0
/*
 * Constructs a fat K_n with the specified number of vertices and edge 
 * multiplicity. The graph is output in multi_code format.
 */
void constructGraph(int vertices, int edgeMultiplicity){
    int i, j, k;
    
    GRAPH graph;
    ADJACENCY adj;
    
    prepareGraph(graph, adj, vertices);
    
    for(i = 1; i < vertices; i++){
        for(j = i+1; j <= vertices; j++){
            for(k = 0; k < edgeMultiplicity; k++){
                addEdge(graph, adj, i, j);
            }
        }
    }
    
    writeMultiCode(graph, adj, stdout);
}
Example #8
0
void decodeMultiCode(unsigned short* code, int length, GRAPH graph, ADJACENCY adj, int *order) {
    int i, currentVertex;
    unsigned short vertexCount;

    *order = vertexCount = code[0];

    prepareGraph(graph, adj, vertexCount);

    //go through code and add edges
    currentVertex = 1;

    for (i = 1; i < length; i++) {
        if (code[i] == 0) {
            currentVertex++;
        } else {
            addEdge(graph, adj, currentVertex, (int) code[i], FALSE);
            if ((adj[code[i]] > MAXVAL) || (adj[currentVertex] > MAXVAL)) {
                fprintf(stderr, "MAXVAL too small (%d)!\n", MAXVAL);
                exit(0);
            }
        }
    }
}
Example #9
0
template <typename captype, typename tcaptype, typename flowtype> flowtype IBFSGraph<captype, tcaptype, flowtype>::maxflow()
{
	node *i, *j, *i_tmp, *prevSrc, *prevSink;
	arc *a, *a_end, *a_tmp;
	AugmentationInfo augInfo;

	prepareGraph();

#ifdef STATS
	numAugs = 0;
	numOrphans = 0;
	grownSinkTree = 0;
	grownSourceTree = 0;

	numPushes = 0;
	orphanArcs1 = 0;
	orphanArcs2 = 0;
	orphanArcs3 = 0;
	growthArcs = 0;

	skippedGrowth = 0;
	numOrphans0 = 0;
	numOrphans1 = 0;
	numOrphans2 = 0;
	augLenMin = 999999;
	augLenMax = 0;
#endif

	//
	// init
	//
	orphanFirst = END_OF_ORPHANS;
	activeFirst1 = END_OF_LIST_NODE;
	activeLevel = 1;
	for (i=nodes; i<nodeLast; i++)
	{
		i->nextActive = NULL;
		i->firstSon = NULL;

		if (i->terminalCap == 0)
		{
			i->parent = NULL;
		}
		else
		{
			i->parent = TERMINAL;
			if (i->terminalCap > 0)
			{
				i->label = 1;
				SET_ACTIVE(i);
			}
			else
			{
				i->label = -1;
				SET_ACTIVE(i);
			}
		}
	}
	activeFirst0 = activeFirst1;
	activeFirst1 = END_OF_LIST_NODE;

	//
	// growth + augment
	//
	prevSrc = NULL;
	prevSink = NULL;
	augInfo.flowDeficit = 0;
	augInfo.flowExcess = 0;
	while (activeFirst0 != END_OF_LIST_NODE)
	{
		//
		// BFS level
		//
		while (activeFirst0 != END_OF_LIST_NODE)
		{
			/*
			i = active_src_first0;
			while (i->nextActive != END_OF_LIST_NODE)
			{
				if (i->parent &&
					i->nextActive->parent &&
					i->label > 0 &&
					i->label != activeLevel_src &&
					i->label != activeLevel_src+1)
				{
					i = active_src_first0;
					printf("flow=%d, active_label=%d, src active ",
						flow, activeLevel_src);
					while (i != END_OF_LIST_NODE)
					{
						if (i->parent &&
							(i->nextActive == END_OF_LIST_NODE ||
							i->nextActive->parent == NULL ||
							i->label != i->nextActive->label))
						{
							printf("%d ", i->label);
						}
						i = i->nextActive;
					}
					printf("\n");
					break;
				}
				i = i->nextActive;
			}
			*/

			i = activeFirst0;
			activeFirst0 = i->nextActive;
			i->nextActive = NULL;
			if (i->parent == NULL)
			{
#ifdef STATS
				skippedGrowth++;
#endif
				continue;
			}
			//if (ABS(i->label) != activeLevel &&
			//	ABS(i->label) != (activeLevel+1))
			//{
//#ifdef FLOATS
			//	printf("ERROR, flow=%f, label=%d, active_label=%d\n",
			//		flow, i->label, activeLevel);
//#else
			//	printf("ERROR, flow=%d, label=%d, active_label=%d\n",
			//		flow, i->label, activeLevel);
//#endif
			//	exit(1);
			//}

			if (i->label > 0)
			{
				//
				// GROWTH SRC
				//
				if (i->label != activeLevel)
				{
#ifdef STATS
					skippedGrowth++;
#endif
					SET_ACTIVE(i);
					continue;
				}

#ifdef STATS
				grownSourceTree++;
#endif
				a_end = (i+1)->firstArc;
				for (a=i->firstArc; a != a_end; a++)
				{
#ifdef STATS
					growthArcs++;
#endif
					if (a->rCap != 0)
					{
						j = a->head;
						if (j->parent == NULL)
						{
							j->label = i->label+1;
							j->parent = a->sister;
							j->nextSibling = NODE_PTR_TO_INDEX(i->firstSon);
							i->firstSon = j;
							SET_ACTIVE(j);
						}
						else if (j->label < 0)
						{
							i->nextActive = activeFirst0;
							activeFirst0 = i;
							if (prevSrc != i)
							{
								augInfo.remainingExcess = 0;
								if (augInfo.flowExcess != 0)
								{
									i_tmp = prevSrc;
									for (; ; i_tmp=a_tmp->head)
									{
										a_tmp = i_tmp->parent;
										if (a_tmp == TERMINAL) break;
										a_tmp->rCap += augInfo.flowExcess;
										a_tmp->sister->sister_rCap = 1;
										a_tmp->sister->rCap -= augInfo.flowExcess;
									}
									i_tmp->terminalCap -= augInfo.flowExcess;
									augInfo.flowExcess = 0;
								}
							}
							if (prevSrc != i || prevSink != j)
							{
								augInfo.remainingDeficit = 0;
								if (augInfo.flowDeficit != 0)
								{
									i_tmp = prevSink;
									for (; ; i_tmp=a_tmp->head)
									{
										a_tmp = i_tmp->parent;
										if (a_tmp == TERMINAL) break;
										a_tmp->sister->rCap += augInfo.flowDeficit;
										a_tmp->sister_rCap = 1;
										a_tmp->rCap -= augInfo.flowDeficit;
									}
									i_tmp->terminalCap += augInfo.flowDeficit;
									augInfo.flowDeficit = 0;
								}
							}
							augment(a, &augInfo);
							prevSrc = i;
							prevSink = j;
							break;
						}
					}
				}
			}
			else
			{
				//
				// GROWTH SINK
				//
				if (-(i->label) != activeLevel)
				{
#ifdef STATS
					skippedGrowth++;
#endif
					SET_ACTIVE(i);
					continue;
				}

#ifdef STATS
				grownSinkTree++;
#endif
				a_end = (i+1)->firstArc;
				for (a=i->firstArc; a != a_end; a++)
				{
#ifdef STATS
					growthArcs++;
#endif
					if (a->sister_rCap != 0)
					{
						j = a->head;
						if (j->parent == NULL)
						{
							j->label = i->label-1;
							j->parent = a->sister;
							j->nextSibling = NODE_PTR_TO_INDEX(i->firstSon);
							i->firstSon = j;
							SET_ACTIVE(j);
						}
						else if (j->label > 0)
						{
							i->nextActive = activeFirst0;
							activeFirst0 = i;
							if (prevSink != i)
							{
								augInfo.remainingDeficit = 0;
								if (augInfo.flowDeficit != 0)
								{
									i_tmp = prevSink;
									for (; ; i_tmp=a_tmp->head)
									{
										a_tmp = i_tmp->parent;
										if (a_tmp == TERMINAL) break;
										a_tmp->sister->rCap += augInfo.flowDeficit;
										a_tmp->sister_rCap = 1;
										a_tmp->rCap -= augInfo.flowDeficit;
									}
									i_tmp->terminalCap += augInfo.flowDeficit;
									augInfo.flowDeficit = 0;
								}
							}
							if (prevSink != i || prevSrc != j)
							{
								augInfo.remainingExcess = 0;
								if (augInfo.flowExcess != 0)
								{
									i_tmp = prevSrc;
									for (; ; i_tmp=a_tmp->head)
									{
										a_tmp = i_tmp->parent;
										if (a_tmp == TERMINAL) break;
										a_tmp->rCap += augInfo.flowExcess;
										a_tmp->sister->sister_rCap = 1;
										a_tmp->sister->rCap -= augInfo.flowExcess;
									}
									i_tmp->terminalCap -= augInfo.flowExcess;
									augInfo.flowExcess = 0;
								}
							}
							augment(a->sister, &augInfo);
							prevSrc = j;
							prevSink = i;
							break;
						}
					}
				}
			}
		}

		augInfo.remainingDeficit = 0;
		if (augInfo.flowDeficit != 0)
		{
			i_tmp = prevSink;
			for (; ; i_tmp=a_tmp->head)
			{
				a_tmp = i_tmp->parent;
				if (a_tmp == TERMINAL) break;
				a_tmp->sister->rCap += augInfo.flowDeficit;
				a_tmp->sister_rCap = 1;
				a_tmp->rCap -= augInfo.flowDeficit;
			}
			i_tmp->terminalCap += augInfo.flowDeficit;
			augInfo.flowDeficit = 0;
			prevSink = NULL;
		}
		augInfo.remainingExcess = 0;
		if (augInfo.flowExcess != 0)
		{
			i_tmp = prevSrc;
			for (; ; i_tmp=a_tmp->head)
			{
				a_tmp = i_tmp->parent;
				if (a_tmp == TERMINAL) break;
				a_tmp->rCap += augInfo.flowExcess;
				a_tmp->sister->sister_rCap = 1;
				a_tmp->sister->rCap -= augInfo.flowExcess;
			}
			i_tmp->terminalCap -= augInfo.flowExcess;
			augInfo.flowExcess = 0;
			prevSrc = NULL;
		}

		//
		// switch to next level
		//
#ifdef COUNT_RELABELS
		for (int k=0; k<scanIndices.size(); k++)
		{
			total++;
			if (scans[scanIndices[k]] <= 10)
			{
				counts[scans[scanIndices[k]]-1]++;
			}
		}
#endif

		activeFirst0 = activeFirst1;
		activeFirst1 = END_OF_LIST_NODE;
		activeLevel++;
	}
	
	return flow;
}