예제 #1
0
// creates a virtual vertex of vertex father and embeds it as
// root in the biconnected child component containing of one edge
void BoyerMyrvoldInit::createVirtualVertex(const adjEntry father)
{
	// check that adjEntry is valid
	OGDF_ASSERT(father != nullptr);

	// create new virtual Vertex and copy properties from non-virtual node
	const node virt = m_g.newNode();
	m_realVertex[virt] = father->theNode();
	m_dfi[virt] = -m_dfi[father->twinNode()];
	m_nodeFromDFI[m_dfi[virt]] = virt;

	// set links for traversal of bicomps
	m_link[CW][virt] = father->twin();
	m_link[CCW][virt] = father->twin();

	// move edge to new virtual Vertex
	edge e = father->theEdge();
	if (e->source() == father->theNode()) {
		// e is outgoing edge
		m_g.moveSource(e,virt);
	} else {
		// e is ingoing edge
		m_g.moveTarget(e,virt);
	}
}
예제 #2
0
bool FeasibleUpwardPlanarSubgraph::constructMergeGraph(
	GraphCopy &M,
	adjEntry adj_orig,
	const List<edge> &orig_edges)
{
	CombinatorialEmbedding Beta(M);

	//set ext. face of Beta
	adjEntry ext_adj = M.copy(adj_orig->theEdge())->adjSource();
	Beta.setExternalFace(Beta.rightFace(ext_adj));

	FaceSinkGraph fsg(Beta, M.copy(adj_orig->theNode()));
	SList<node> aug_nodes;
	SList<edge> aug_edges;
	SList<face> fList;
	fsg.possibleExternalFaces(fList); // use this method to call the methode checkForest()
	node v_ext = fsg.faceNodeOf(Beta.externalFace());

	OGDF_ASSERT(v_ext != 0);

	fsg.stAugmentation(v_ext, M, aug_nodes, aug_edges);

	//add the deleted edges
	for(edge eOrig: orig_edges) {
		node a = M.copy(eOrig->source());
		node b = M.copy(eOrig->target());
		M.newEdge(a, b);
	}
	return (isAcyclic(M));
}
예제 #3
0
BitonicOrdering::BitonicOrdering(Graph& G, adjEntry adj_st_edge)
  : m_graph(G)
  , m_currLabel(0)
  , m_orderIndex(G,-1)
  , m_indexToNode(G.numberOfNodes())
  , m_tree(G, adj_st_edge->theEdge(), true)
{
    // set all tree nodes to non flipped
    m_flipped.init(m_tree.tree(), false);

    // s in the graph
    node s_G = adj_st_edge->theNode();
    node t_G = adj_st_edge->twinNode();

    // we label s here manually: set the label
    m_orderIndex[s_G] = m_currLabel++;
    // and update the other map
    m_indexToNode[m_orderIndex[s_G]] = s_G;

    // label everything else except t
    handleCase(m_tree.rootNode());

    // we label s here manually: set the label
    m_orderIndex[t_G] = m_currLabel++;
    // and update the other map
    m_indexToNode[m_orderIndex[t_G]] = t_G;

    // finally embedd G
    m_tree.embed(m_graph);
}
예제 #4
0
string print_arc_string(adjEntry a)
{
  sprintf(buf, "%d->%d", a->theNode()->index(), a->twinNode()->index());

  string res = buf;
  return res;
}
예제 #5
0
void PlanarSPQRTree::setPosInEmbedding(
	NodeArray<SListPure<adjEntry> > &adjEdges,
	NodeArray<node> &currentCopy,
	NodeArray<adjEntry> &lastAdj,
	SListPure<node> &current,
	const Skeleton &S,
	adjEntry adj)
{
	node vT = S.treeNode();

	adjEdges[vT].pushBack(adj);

	node vCopy = adj->theNode();
	node vOrig = S.original(vCopy);

	if(currentCopy[vT] == nullptr) {
		currentCopy[vT] = vCopy;
		current.pushBack(vT);

		for (adjEntry adjVirt : vCopy->adjEdges) {
			edge eCopy = S.twinEdge(adjVirt->theEdge());
			if (eCopy == nullptr) continue;
			if (adjVirt == adj) {
				lastAdj[vT] = adj;
				continue;
			}

			const Skeleton &STwin = skeleton(S.twinTreeNode(adjVirt->theEdge()));

			adjEntry adjCopy = (STwin.original(eCopy->source()) == vOrig) ?
				eCopy->adjSource() : eCopy->adjTarget();

			setPosInEmbedding(adjEdges,currentCopy,lastAdj,current,
				STwin, adjCopy);
		}

	} else if (lastAdj[vT] != nullptr && lastAdj[vT] != adj) {
		adjEntry adjVirt = lastAdj[vT];
		edge eCopy = S.twinEdge(adjVirt->theEdge());

		const Skeleton &STwin = skeleton(S.twinTreeNode(adjVirt->theEdge()));

		adjEntry adjCopy = (STwin.original(eCopy->source()) == vOrig) ?
			eCopy->adjSource() : eCopy->adjTarget();

		setPosInEmbedding(adjEdges,currentCopy,lastAdj,current,
			STwin, adjCopy);

		lastAdj[vT] = nullptr;
	}

}
예제 #6
0
파일: FUPSSimple.cpp 프로젝트: lncosie/ogdf
bool FUPSSimple::constructMergeGraph(GraphCopy &M, adjEntry adj_orig, const List<edge> &orig_edges)
{
	CombinatorialEmbedding Beta(M);

	//set ext. face of Beta
	adjEntry ext_adj = M.copy(adj_orig->theEdge())->adjSource();
	Beta.setExternalFace(Beta.rightFace(ext_adj));

	//*************************** debug ********************************
	/*
	cout << endl << "FUPS : " << endl;
	for(face ff : Beta.faces) {
		cout << "face " << ff->index() << ": ";
		adjEntry adjNext = ff->firstAdj();
		do {
			cout << adjNext->theEdge() << "; ";
			adjNext = adjNext->faceCycleSucc();
		} while(adjNext != ff->firstAdj());
		cout << endl;
	}
	if (Beta.externalFace() != 0)
		cout << "ext. face of the graph is: " << Beta.externalFace()->index() << endl;
	else
		cout << "no ext. face set." << endl;
	*/

	FaceSinkGraph fsg(Beta, M.copy(adj_orig->theNode()));
	SList<node> aug_nodes;
	SList<edge> aug_edges;
	SList<face> fList;
	fsg.possibleExternalFaces(fList); // use this method to call the methode checkForest()
	node v_ext = fsg.faceNodeOf(Beta.externalFace());

	OGDF_ASSERT(v_ext != 0);

	fsg.stAugmentation(v_ext, M, aug_nodes, aug_edges);

	/*
	//------------------------------------debug
	GraphAttributes AG(M, GraphAttributes::nodeGraphics|
						GraphAttributes::edgeGraphics|
						GraphAttributes::nodeColor|
						GraphAttributes::edgeColor|
						GraphAttributes::nodeLabel|
						GraphAttributes::edgeLabel
						);
	// label the nodes with their index
	for(node v : AG.constGraph().nodes) {
		AG.label(v) = to_string(v->index());
	}
	AG.writeGML("c:/temp/MergeFUPS.gml");
	*/


	OGDF_ASSERT(isStGraph(M));

	//add the deleted edges
	for(edge eOrig : orig_edges) {
		node a = M.copy(eOrig->source());
		node b = M.copy(eOrig->target());
		M.newEdge(a, b);
	}
	return (isAcyclic(M));
}
예제 #7
0
void FPPLayout::computeOrder(
	const GraphCopy &G,
	NodeArray<int> &num,
	NodeArray<adjEntry> &e_wp,
	NodeArray<adjEntry> &e_wq,
	adjEntry e_12,
	adjEntry e_2n,
	adjEntry e_n1)
{
	NodeArray<int> num_diag(G, 0);							// number of chords
	// link[v] = Iterator in possible, that points to v (if diag[v] = 0 and outer[v] = TRUE)
	NodeArray<ListIterator<node> > link(G, 0);
	// outer[v] = TRUE <=> v is a node of the actual outer face
	NodeArray<bool> outer(G, false);
	// List of all nodes v with outer[v] = TRUE and diag[v] = 0
	List<node> possible;

	// nodes of the outer triangle (v_1,v_2,v_n)
	node v_1 = e_12->theNode();
	node v_2 = e_2n->theNode();
	node v_n = e_n1->theNode();
	node v_k, wp, wq, u;
	adjEntry e, e2;
	int k;

	// initialization: beginn with outer face (v_1,v_2,v_n)
	// v_n is the only possible node
	num[v_1] = 1;
	num[v_2] = 2;

	outer[v_1] = true;
	outer[v_2] = true;
	outer[v_n] = true;

	link[v_n] = possible.pushBack(v_n);

	e_wq[v_1] = e_n1->twin();
	e_wp[v_2] = e_2n;

	e_wq[v_n] = e_2n->twin();
	e_wp[v_n] = e_n1;

	// select next v_k and delete it
	for (k = G.numberOfNodes(); k >= 3; k--) {
		v_k = possible.popFrontRet();	// select arbitrary node from possible as v_k

		num[v_k] = k;

		// predecessor wp and successor wq from vk in C_k (actual outer face)
		wq = (e_wq [v_k])->twinNode();
		wp = (e_wp [v_k])->twinNode();

		// v_k not in C_k-1 anymore
		outer[v_k] = false;

		// shortfall of a chord?
		if (e_wq[wp]->cyclicSucc()->twinNode() == wq) {   // wp, wq is the only successor of vk in G_k
			// wp, wq loose a chord
			if (--num_diag[wp] == 0) {
				link[wp] = possible.pushBack(wp);
			}
			if (--num_diag[wq] == 0) {
				link[wq] = possible.pushBack(wq);
			}
		}

		// update or initialize e_wq, e_wp
		e_wq[wp] = e_wq[wp]->cyclicSucc();

		e_wp[wq] = e_wp[wq]->cyclicPred();
		e = e_wq[wp];
		for (u = e->twinNode(); u != wq; u = e->twinNode()) {
			outer[u] = true;
			e_wp[u] = e->twin();
			e = e_wq[u] = e_wp[u]->cyclicSucc()->cyclicSucc();

			// search for new chords
			for (e2 = e_wp[u]->cyclicPred(); e2 != e_wq[u]; e2 = e2->cyclicPred()) {
				node w = e2->twinNode();
				if (outer[w] == true) {
					++num_diag[u];
					if (w != v_1 && w != v_2)
						if (++num_diag[w] == 1) possible.del(link[w]);
				}
			}

			if (num_diag[u] == 0) {
				link[u] = possible.pushBack(u);
			}
		}
	}
}
예제 #8
0
void print_arc(adjEntry a)
{
  printf(" %d->%d", a->theNode()->index(), a->twinNode()->index());
}