簡體   English   中英

計算樹中的所有節點

[英]Counting all nodes in a tree

這是我當前的代碼。 它工作正常,但是我無法找到將根節點添加到計數中的方法,因為由於程序是遞歸的,因此總是會多次添加根節點。

int countTree(tnode<T> *t)
{

int count = 0;


 if (t != NULL)
 {
     count = count + countTree(t->left);

if (t->left)
    { count++; }

  count = count + countTree(t->right);

if (t->right)
    { count++; }
}


return count;

};

二叉樹中節點計數的通常遞歸是1 + count(left sub-tree) + count(right sub-tree) ,其中count(null)返回0。

因此,它將類似於:

int count(node *root)
{
    if (!root) { return 0; }

    return 1 + count(root->left) + count(root->right);
}

嘗試這個...

int countTree(tnode<T> *t)
{  
 if (t==NULL)
    return 0;
 return 1+countTree(t->left)+countTree(t-right);
}

或者如何在僅在每個節點上調用一次方法時迭代樹

這取決於您的樹實現,這是一個基於boost::intrusive數據結構和算法的樹示例(其修復尚未在boost發布)。 要點如下:

  • header節點(根)不是樹的一部分,它的左節點指向第一個節點,最后一個節點指向最后一個項目,標頭節點本身是結束迭代器節點
  • next next()next()返回下一個節點, next()按順序返回下一個節點-當它到達底部時(在示例中為3),它返回頂部,然后找到下一個minimum()節點(在這種情況下為5) 。

示例代碼

#include <iostream>

struct node {
    int value;

    node * left;
    node * right;
    node * parent;

    node( int v )
        : value( v )
        , left( nullptr )
        , right( nullptr )
        , parent( nullptr )
    {}

    node() : node( 0 ) {}
    ~node() {}
};

打印節點:

std::ostream & operator<<( std::ostream & os, const node * n ) {
    return os << ( n ? n->value : 0 );
}

迭代:

node * minimum( node * n ) {
    for ( node * l = n->left; l; l = n->left ) n = l;
    return n;
}

node * maximum( node * n ) {
    for ( node * r = n->right; r; r = n->right) n = r;
    return n;
}

node * next( node * n ) {
    if ( ! n ) return nullptr;
    if ( n->right ) return minimum( n->right );
    node * p = n;
    node * x = p->parent;
    while ( p == x->right ) {
        p = x;
        x = x->parent;
    }
    return p->right != x ? x : p;
}

node * prev( node * n ) {
    if ( ! n ) return nullptr;
    if ( n->left ) return maximum( n->left );
    node * p = n;
    node * x = p->parent;
    while ( p == x->left ) {
        p = x;
        x = x->parent;
    }
    return p->left != x ? x : p;
}

簡單的迭代器使用next()找出下一步要訪問的內容:

void iterate( node * root, void(*func)( node * n ) ) {

    node * n = root->left;
    node * e = root;

    while ( n != e and n ) {
        func( n );
        n = next( n );
    }
}

用這個來計數:

static void counter( node * n ) {
    static uint count( 0 );
    ++count;
    std::cout << count << " node [" << n  << "]" << std::endl;
}

樹看起來像這樣:

/*
 * a binary tree
 * for each node, left nodes are smaller, right nodes are bigger
 *
 * header node is just a header node, not part of a tree
 * header.left points to the "first node" in example below to 3
 * header.right points to the "last node" in the example below 2
 * end iterator is the header itself
 * header node is not part of a tree
 *

  --------  R ------
  |         |      |
  |         4      |
  |       /   \    |
  |     2      5 < +
  |    /  \
  +> 1     3
*/

手動創建樹-無論如何,您都將使用boost::intrusive而不是此代碼...

void test() {
    node r( 999 );

    node n1( 1 );
    node n2( 2 );
    node n3( 3 );
    node n4( 4 );
    node n5( 5 );

    // setup n2
    n2.left = & n1;
    n2.right = & n3;

    n1.parent = & n2;
    n3.parent = & n2;

    // setup n4

    n4.left = & n2;
    n2.parent = & n4;

    n4.right = & n5;
    n5.parent = & n4;
    n4.parent = & r;

    // setup header node - header not part of a tree

    r.left = & n1;
    r.right = & n5;

    iterate( & r, & counter );
}

int main() {
    test();
}

結果:

1 node [1]
2 node [2]
3 node [3]
4 node [4]
5 node [5]

占每個節點,不包括頭節點。 不確定是否有幫助。

只要有一個環繞countTree並在第一個節點不為null時加1的函數即可。

例如,

int BaseCountFunc(tnode<T> *t)
{
    int returnValue;

    returnValue = 0;

    if (t!=nullptr)
    {
        returnValue = 1 + countTree(t->left) + countRight(t->right);
    }

    return returnValue;
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM