📜  二叉树中任何路径的1的计数

📅  最后修改于: 2021-04-22 03:13:59             🧑  作者: Mango

给定二叉树为0和1s,任务是在树的任何路径中找到最大1s数。该路径可以在树中的任何节点处开始和结束。

范例

Input: 
       1
      / \
     0   1
    / \
   1   1
      / \
     1   0

Output: 4

方法:

  1. 已创建一个函数countUntil,该函数在该节点下方的任何垂直路径中返回最大计数1。
  2. 该路径必须是单个路径,并且该路径必须包括节点的至少一个子节点及其本身。即countUntil返回左孩子右孩子的最大计数1,并且如果其值为1,也将自身包括在计数中。
  3. 因此,从任何节点开始, countUntil(node-> left)+ countUntil(node-> right)+ node->值将在包含该节点及其左,右路径且该节点没有祖先的路径中给出1的数目被认为。
  4. 取所有节点的最大值将给出所需的答案。

下面是上述方法的实现

C++
// C++ implementation of the above approach
#include 
using namespace std;
  
// A binary tree node
struct Node {
    int data;
    struct Node *left, *right;
};
  
// A utility function to allocate a new node
struct Node* newNode(int data)
{
    struct Node* newNode = new Node;
    newNode->data = data;
    newNode->left = newNode->right = NULL;
    return (newNode);
}
  
// This function updates overall count of 1 in 'res'
// And returns count 1s going through root.
int countUntil(Node* root, int& res)
{
    // Base Case
    if (root == NULL)
        return 0;
  
    // l and r store count of 1s going through left and
    // right child of root respectively
    int l = countUntil(root->left, res);
    int r = countUntil(root->right, res);
  
    // maxCount represents the count of 1s when the Node under
    // consideration is the root of the maxCount path and no
    // ancestors of the root are there in maxCount path
    int maxCount;
  
    // if the value at node is 1 then its
    // count will be considered
    // including the leftCount and the rightCount
    if (root->data == 1)
        maxCount = l + r + 1;
    else
        maxCount = l + r;
  
    // Store the Maximum Result.
    res = max(res, maxCount);
  
    // return max count in a single path.
    // This path must include at-most one child
    // of the root as well as itself
  
    // if the value at node is 1
    // then its count will be considered
    // including the maximum of leftCount or the rightCount
    if (root->data == 1)
        return max(l, r) + 1;
    else
        return max(l, r);
}
  
// Returns maximum count of 1 in any path
// in tree with given root
int findMaxCount(Node* root)
{
    // Initialize result
    int res = INT_MIN;
  
    // Compute and return result
    countUntil(root, res);
    return res;
}
  
// Driver program
int main(void)
{
    struct Node* root = newNode(1);
    root->left = newNode(0);
    root->right = newNode(1);
    root->left->left = newNode(1);
    root->left->right = newNode(1);
    root->left->right->left = newNode(1);
    root->left->right->right = newNode(0);
    cout << findMaxCount(root);
    return 0;
}


Java
// Java implementation of the above approach
class GFG
{
  
    // A binary tree node
    static class Node 
    {
        int data;
        Node left, right;
    };
  
    static int res;
  
    // A utility function to allocate a new node
    static Node newNode(int data)
    {
        Node newNode = new Node();
        newNode.data = data;
        newNode.left = newNode.right = null;
        return (newNode);
    }
  
    // This function updates overall count of 1 in 'res'
    // And returns count 1s going through root.
    static int countUntil(Node root) 
    {
        // Base Case
        if (root == null)
            return 0;
  
        // l and r store count of 1s going through left and
        // right child of root respectively
        int l = countUntil(root.left);
        int r = countUntil(root.right);
  
        // maxCount represents the count of 1s when the Node under
        // consideration is the root of the maxCount path and no
        // ancestors of the root are there in maxCount path
        int maxCount;
  
        // if the value at node is 1 then its
        // count will be considered
        // including the leftCount and the rightCount
        if (root.data == 1)
            maxCount = l + r + 1;
        else
            maxCount = l + r;
  
        // Store the Maximum Result.
        res = Math.max(res, maxCount);
  
        // return max count in a single path.
        // This path must include at-most one child
        // of the root as well as itself
  
        // if the value at node is 1
        // then its count will be considered
        // including the maximum of leftCount or the rightCount
        if (root.data == 1)
            return Math.max(l, r) + 1;
        else
            return Math.max(l, r);
    }
  
    // Returns maximum count of 1 in any path
    // in tree with given root
    static int findMaxCount(Node root) 
    {
        // Initialize result
        res = Integer.MIN_VALUE;
  
        // Compute and return result
        countUntil(root);
        return res;
    }
  
    // Driver program
    public static void main(String[] args)
    {
        Node root = newNode(1);
        root.left = newNode(0);
        root.right = newNode(1);
        root.left.left = newNode(1);
        root.left.right = newNode(1);
        root.left.right.left = newNode(1);
        root.left.right.right = newNode(0);
        System.out.print(findMaxCount(root));
    }
}
  
// This code is contributed by 29AjayKumar


Python3
# Python implementation of the above approach
  
# A binary tree node
class Node:
    def __init__(self):
        self.data = 0
        self.left = None
        self.right = None
  
# A utility function to allocate a new node
def newNode(data):
  
    newNode = Node()
    newNode.data = data
    newNode.left = newNode.right = None
    return (newNode)
  
res = 0
  
# This function updates overall count of 1 in 'res'
# And returns count 1s going through root.
def countUntil( root):
    global res
      
    # Base Case
    if (root == None):
        return 0
  
    # l and r store count of 1s going through left and
    # right child of root respectively
    l = countUntil(root.left)
    r = countUntil(root.right)
  
    # maxCount represents the count of 1s when the Node under
    # consideration is the root of the maxCount path and no
    # ancestors of the root are there in maxCount path
    maxCount = 0
  
    # if the value at node is 1 then its
    # count will be considered
    # including the leftCount and the rightCount
    if (root.data == 1):
        maxCount = l + r + 1
    else:
        maxCount = l + r
  
    # Store the Maximum Result.
    res = max(res, maxCount)
  
    # return max count in a single path.
    # This path must include at-most one child
    # of the root as well as itself
  
    # if the value at node is 1
    # then its count will be considered
    # including the maximum of leftCount or the rightCount
    if (root.data == 1):
        return max(l, r) + 1
    else:
        return max(l, r)
  
# Returns maximum count of 1 in any path
# in tree with given root
def findMaxCount(root):
      
    global res
  
    # Initialize result
    res = -999999
  
    # Compute and return result
    countUntil(root)
    return res
  
# Driver program
  
root = newNode(1)
root.left = newNode(0)
root.right = newNode(1)
root.left.left = newNode(1)
root.left.right = newNode(1)
root.left.right.left = newNode(1)
root.left.right.right = newNode(0)
print(findMaxCount(root))
  
# This code is contributed by Arnab Kundu


C#
// C# implementation of the above approach
using System;
  
class GFG
{
  
    // A binary tree node
    class Node 
    {
        public int data;
        public Node left, right;
    };
  
    static int res;
  
    // A utility function to allocate a new node
    static Node newNode(int data)
    {
        Node newNode = new Node();
        newNode.data = data;
        newNode.left = newNode.right = null;
        return (newNode);
    }
  
    // This function updates overall count of 1 in 'res'
    // And returns count 1s going through root.
    static int countUntil(Node root) 
    {
        // Base Case
        if (root == null)
            return 0;
  
        // l and r store count of 1s going through left and
        // right child of root respectively
        int l = countUntil(root.left);
        int r = countUntil(root.right);
  
        // maxCount represents the count of 1s when the Node under
        // consideration is the root of the maxCount path and no
        // ancestors of the root are there in maxCount path
        int maxCount;
  
        // if the value at node is 1 then its
        // count will be considered
        // including the leftCount and the rightCount
        if (root.data == 1)
            maxCount = l + r + 1;
        else
            maxCount = l + r;
  
        // Store the Maximum Result.
        res = Math.Max(res, maxCount);
  
        // return max count in a single path.
        // This path must include at-most one child
        // of the root as well as itself
  
        // if the value at node is 1
        // then its count will be considered
        // including the maximum of leftCount or the rightCount
        if (root.data == 1)
            return Math.Max(l, r) + 1;
        else
            return Math.Max(l, r);
    }
  
    // Returns maximum count of 1 in any path
    // in tree with given root
    static int findMaxCount(Node root) 
    {
        // Initialize result
        res = int.MinValue;
  
        // Compute and return result
        countUntil(root);
        return res;
    }
  
    // Driver program
    public static void Main(String[] args)
    {
        Node root = newNode(1);
        root.left = newNode(0);
        root.right = newNode(1);
        root.left.left = newNode(1);
        root.left.right = newNode(1);
        root.left.right.left = newNode(1);
        root.left.right.right = newNode(0);
        Console.Write(findMaxCount(root));
    }
}
  
// This code is contributed by PrinciRaj1992


输出:
4

时间复杂度: O(n)
其中n是二叉树中的节点数。