Esempio n. 1
0
/*
 * computes the sizes of all subtrees of a tree with root r
 */
void SchnyderLayout::subtreeSizes(
	EdgeArray<int>& rValues,
	int i,
	node r,
	NodeArray<int>& size)
{
	int sum = 0;
	for(adjEntry adj : r->adjEdges) {
		if (adj->theEdge()->source() == r && rValues[adj->theEdge()] == i) {
			node w = adj->twinNode();
			subtreeSizes(rValues, i, w, size);
			sum += size[w];
		}
	}
	size[r] = sum + 1;
}
static TVector<TVector<size_t>> CalcSubtreeSizesForTree(const TObliviousTrees& forest, size_t treeIdx) {
    const int maxDepth = forest.TreeSizes[treeIdx];
    TVector<TVector<size_t>> subtreeSizes(maxDepth + 1);

    subtreeSizes[maxDepth].resize(size_t(1) << maxDepth);
    for (size_t leafIdx = 0; leafIdx < (size_t(1) << maxDepth); ++leafIdx) {
        subtreeSizes[maxDepth][leafIdx] = size_t(forest.LeafWeights[treeIdx][leafIdx] + 0.5);
    }

    for (int depth = maxDepth - 1; depth >= 0; --depth) {
        const size_t nodeCount = size_t(1) << depth;
        subtreeSizes[depth].resize(nodeCount);
        for (size_t nodeIdx = 0; nodeIdx < nodeCount; ++nodeIdx) {
            subtreeSizes[depth][nodeIdx] = subtreeSizes[depth + 1][nodeIdx] + subtreeSizes[depth + 1][nodeIdx ^ (1 << depth)];
        }
    }
    return subtreeSizes;
}
Esempio n. 3
0
void SchnyderLayout::schnyderEmbedding(
	GraphCopy& GC,
	GridLayout &gridLayout,
	adjEntry adjExternal)
{
	NodeArray<int> &xcoord = gridLayout.x();
	NodeArray<int> &ycoord = gridLayout.y();

	node v;
	List<node> L;						// (un)contraction order
	GraphCopy T = GraphCopy(GC);		// the realizer tree (reverse direction of edges!!!)
	EdgeArray<int> rValues(T);			// the realizer values

	// choose outer face a,b,c
	adjEntry adja;
	if (adjExternal != 0) {
		edge eG  = adjExternal->theEdge();
		edge eGC = GC.copy(eG);
		adja = (adjExternal == eG->adjSource()) ? eGC->adjSource() : eGC->adjTarget();
	}
	else {
		adja = GC.firstEdge()->adjSource();
	}
	adjEntry adjb = adja->faceCyclePred();
	adjEntry adjc = adjb->faceCyclePred();

	node a = adja->theNode();
	node b = adjb->theNode();
	node c = adjc->theNode();

	node a_in_T = T.copy(GC.original(a));
	node b_in_T = T.copy(GC.original(b));
	node c_in_T = T.copy(GC.original(c));

	contract(GC, a, b, c, L);

	realizer(GC, L, a, b, c, rValues, T);

	NodeArray<int>  t1(T);
	NodeArray<int>  t2(T);
	NodeArray<int>  val(T, 1);

	NodeArray<int>  P1(T);
	NodeArray<int>  P3(T);
	NodeArray<int>  v1(T);
	NodeArray<int>  v2(T);

	subtreeSizes(rValues, 1, a_in_T, t1);
	subtreeSizes(rValues, 2, b_in_T, t2);

	prefixSum(rValues, 1, a_in_T, val, P1);
	prefixSum(rValues, 3, c_in_T, val, P3);
	// now Pi  =  depth of all nodes in Tree T(i) (depth[root] = 1)

	prefixSum(rValues, 2, b_in_T, t1, v1);
	// special treatment for a
	v1[a_in_T] = t1[a_in_T];

	/*
	 * v1[v] now is the sum of the
	 * "count of nodes in t1" minus the "subtree size for node x"
	 * for every node x on a path from b to v in t2
	 */

	prefixSum(rValues, 3, c_in_T, t1, val);
	// special treatment for a
	val[a_in_T] = t1[a_in_T];

	/*
	 * val[v] now is the sum of the
	 * "count of nodes in t1" minus the "subtree size for node x"
	 * for every node x on a path from c to v in t3
	 */

	// r1[v]=v1[v]+val[v]-t1[v] is the number of nodes in region 1 from v
	forall_nodes(v, T) {
		// calc v1'
		v1[v] += val[v] - t1[v] - P3[v];
	}