C#
 Computer >> コンピューター >  >> プログラミング >> C#

C#で二分木に指定した合計値となるパスが存在するか判定する方法

二分木において、ルートから葉までの経路(パス)上のノード値の合計が、指定された値と一致するかどうかを判定する問題は、木構造のアルゴリズム学習における定番テーマの一つです。この記事では、C#を使ってこの問題を再帰的に解く方法を解説します。

アルゴリズムの考え方

HasPathSum メソッドは、2つの引数を受け取ります。1つ目は木のノード、2つ目は目標となる合計値です。

処理の流れは以下のとおりです。

  1. 最初にノードが null かどうかをチェックします。ノードが null の場合は false を返します。
  2. ノードが null でなければ、再帰メソッド helperHasPathSum を呼び出します。
  3. 再帰の各ステップでは、現在のノードの値を合計値から引き算していきます。
  4. 葉ノード(左右の子を持たないノード)に到達した時点で合計値がちょうど 0 になっていれば、「指定された合計値に等しいパスが存在する」と判断し、true を返します。

このように「残りの合計値」を親から子へ渡しながら減算していくことで、各パスの合計が目標値と一致するかを効率的に判定できます。

実装例

public class TreesPgm{
    public class Node{
        public int Value;
        public Node LeftChild;
        public Node RightChild;
        public Node(int value){
            this.Value = value;
        }
        public override String ToString(){
            return "Node=" + Value;
        }
    }
    public bool HasPathSum(Node node, int sum){
        if (node == null){
            return false;
        }
        return helperHasPathSum(node, sum);
    }
    private bool helperHasPathSum(Node root, int sum){
        if (root == null){
            return false;
        }
        sum -= root.Value;
        if (root.LeftChild == null && root.RightChild == null && sum == 0){
            return true;
        }
        return helperHasPathSum(root.LeftChild, sum) || helperHasPathSum(root.RightChild, sum);
    }
}

ポイントとして、公開メソッド HasPathSumnull チェックを行い、実際の再帰処理はプライベートメソッド helperHasPathSum に分離しています。これによりコードの責務が明確になり、可読性が向上します。また、葉ノードの判定を root.LeftChild == null && root.RightChild == null で行うことで、途中のノードで合計が 0 になっても誤って true を返さないようになっています。

入力例

          5
      2       6
   1     3
7

出力結果

True

この例では、たとえば「5 → 2 → 3」というパスの合計が 10 になるため、指定した合計値に一致するパスが存在することになり、結果は True となります。

計算量について

このアルゴリズムは各ノードを一度だけ訪問するため、時間計算量は O(n)(n はノード数)です。また、再帰呼び出しの深さは木の高さに依存するため、空間計算量は最悪の場合 O(n)、バランスの取れた木では O(log n) となります。

  1. Pythonで二分木の中から最大のBST(二分探索木)の合計値を見つけるプログラム

    問題の概要ある二分木が与えられたとします。この木の部分木の中に二分探索木(BST)が存在するかどうかを調べ、その中で最も大きなBSTを見つけ出し、そのノード値の合計を求めるのが目的です。合計値は、そのBSTに含まれる各ノードの値をすべて足し合わせたものになります。例えば、入力が次のような二分木だったとしましょう。この場合、出力は 12 となります。与えられた二分木の中に存在するBSTは次の部分木です。このBSTのノード値の合計 = 12 となります。解き方のアプローチこの問題を解くために、以下の手順で処理を進めます。変数 c := 0、m := null、value := 0 を初期化します。

  2. Pythonで解く二分木の最大パス和(Maximum Path Sum)

    問題の概要空でない二分木が1つ与えられます。この木における「最大パス和」を求めるのが目的です。ここでいうパスとは、あるノードを起点として、親子関係で結ばれたノードをたどり任意のノードへ至るまでのノード列のことです。パスには少なくとも1つのノードが含まれている必要がありますが、必ずしも根(ルート)ノードを通る必要はありません。例として、次のような二分木が入力された場合を考えてみましょう。この場合の出力は 32 となります。アルゴリズムの考え方各ノードを「パスの折り返し地点」として捉えるのがポイントです。あるノードを頂点とするパスの和は、「左部分木からの最大寄与 + 右部分木からの最大寄与 + そ