2017-08-10 13 views
0

、私は次のように定義されたバイナリツリーがあります。私のプログラムでこのポインタの算術演算が機能しないのはなぜですか?私のプログラムで

struct node { 
    char value; 
    struct node *left, *right; 
}; 

を、私は、インデックスのために、各ノードの値の文字列を返す関数(上下を書き込もうとしています、右から左への走査)。そうする試みにおいて

は、私は次の関数を書かれている:それは動作するはずのよう

char *to_string_util(struct node *root, char *str) { 

    if (!root) return str; 

    *str++ = root->value; 

    // If not NULL 
    if (root->left) to_string_util(root->left, str); 
    if (root->right) to_string_util(root->right, str); 

    return str; 
} 

これがようだが、残念ながら、それはしていません。私はそれが動作しますが、別の変数の導入を必要とするので望ましくない配列の索引付けを使用して動作させるようにしました。ここで

は作品のバージョンは次のとおりです。

ツリーを考える
char *to_string_util(struct node *root, char *str, int *cur_pos) { 

    if (!root) return str; 

    str[(*cur_pos)++] = root->value; 

    if (root->left) to_string_util(root->left, str, cur_pos); 

    if (root->right) to_string_util(root->right, str, cur_pos); 

    return str; 
} 

   + 
     / \ 
      *  * 
     /\ /\ 
     a a b b 

結果は次のようになります。注意すべき+*aa*bb

一つは、私は、この関数を呼び出すことですその最後にヌル文字を追加する別の関数ですが、出力には影響しないはずですが、言及する価値があると思いました。

なぜ2番目のバージョンは配列インデックスを使用していますが、最初の配列は機能しません。

答えて

4

再帰的なサブ呼び出しから返された新しい値strを無視しているため、機能しません。あなたの関数はstrの値を更新し、return str;を実行して新しい値を返すように設計されています。そして、あなたは戻り値を破棄しているだけです。このため、各再帰レベルで、右サブツリーの呼び出しは、左サブツリーへの再帰呼び出しによって書き込まれたデータを上書きします。

これはおそらく、あなたの心

// If not NULL 
if (root->left) str = to_string_util(root->left, str); 
if (root->right) str = to_string_util(root->right, str); 

そして、もちろん、あなたが最後にあなたの文字列をゼロに終了するように心がけてくださいしていたものに近いです。


関数が

if (!root) return str; 

で始まる場合は、再帰的なサブ呼び出しが本当にヌルチェックを必要としない、あなたはそれを見ていない限り

str = to_string_util(root->left, str); 
str = to_string_util(root->right, str); 

(のように簡略化することができます最適化として)。


あなたのインデックスベースのバージョンは、もはやstrの更新に依存しない(とまったく更新されません)。ポジション値*cur_posの更新によって異なります。位置値は、参照番号によって異なるレベルの再帰レベルの間で渡されるため、すべてのレベルの再帰でこれらの更新が参照されます。

最初のバージョンでも同じ手法を使用できます。参照番号にポインタを渡してください。しかし、そのためにはstrchar **str(ポインタへのポインタ)として渡し、*strと現在の文字ポインタを使用する必要があります。

関連する問題