3

Python で再帰メソッドの問題が発生しました。コードは次のとおりです。

class NodeTree(object):
    def __init__(self, name, children):
        self.name = name
        self.children = children

    def count(self):
        # 1 + i children's nodes
        count = 1
        for c in self.children:
            count += c.count()
        return count


def create_tree(d):
    N = NodeTree(d['name'], d['children'])
    print N.count()

d1 = {'name':'musica', 'children':[{'name':'rock', 'children':[{'name':'origini','children':[]},
                                                               {'name':'rock&roll','children':[]},
                                                               {'name':'hard rock', 'children':[]}]},
                                   {'name':'jazz', 'children':[{'name':'origini', 'children':[{'name':'1900', 'children':[]}]},
                                                               {'name':'ragtime', 'children':[]}, {'name':'swing', 'children':[]}]}]}
tree = create_tree(d1)

エラーは次のとおりです。

count += c.count()
AttributeError: 'dict' object has no attribute 'count'

私は何でも試しましたが、うまくいきません。

とにかく、何か提案はありますか?ありがとう!

4

4 に答える 4

1

countこれは、Python 辞書にメソッドがないためです。

コードが実際に行っていることを 1 行ずつ確認すると役に立ちます。

    デフカウント(自己):
        # 1 + i 子ノード
        カウント = 1
        for c in self.children: ## self.children は辞書のリストなので、各 c は辞書です
            count += c.count() ## 辞書である c の .count() を取得しています
        リターンカウント

これは、辞書のリストである self.children として d1['children'] を渡したためです[<dict>, <dict>, <dict>, ... ]

ではなく、辞書count()を呼び出しlenて、辞書にあるキーの数を取得することで、次のようになります。

    for c in self.children:
        count += len(c)
于 2012-12-04T19:45:42.763 に答える
0

最良の (そして唯一望ましい) 方法は、ノード ツリーを再帰的に作成することです。これは、2 つの異なる方法で行うことができます。NodeTree.__init__()すべての子を再帰的に初期化するか (すべての子を再帰的に初期化するなど)、create_tree()関数を再帰的にすることができます。

私は個人的に recursive__init__()を使用しますが、それはあなたの呼び出しです。


__init__()ツリー構造を作成するための再帰的:

def __init__(self, name, children=[]):
    self.name = name
    self.children = []
    for c in children:
        self.children.append(
            self.__class__(c['name'], c['children']))

この方法には、の代わりにself.children他の が含まれます。また、次の代わりに、空の子リストを宣言する必要がなくなりました。NodeTreedict

d2 = {'name':'sterile', 'children':[]}

行う

d2 = {'name':'sterile'}

そして、イニシャライザは自動的に子を[]


再帰関数を使用したい場合はcreate_tree()、それも可能であり、悪い考えでもありません。ただし、-method を編集する必要はありますが__init__()、子をパラメーターとして取りません。または、私がここで行ったように、使用しますが、ほとんど使用しません。

# NodeTree
def __init__(self, name, children=None):
    self.name = name
    if children:
        self.children = children

def create_tree(d):
    N = NodeTree(d['name'])
    for c in d['children']:
        N.children.append(create_tree(c))
    return N

これは基本的に同じ結果になります。

于 2012-12-05T12:07:28.347 に答える
0

d['children']dictlist of dictでわかるように、です。d1

ここで、基本的にのみであるchildreninを反復処理すると、各要素として次のようになります。NodeTreed['children']dictionary

for c in self.children:  // c is a `dict` type here
    count += c.count()   // there is not attribute as `count` for a `dict`.

したがって、そのエラーが発生しました。

于 2012-12-04T19:43:29.273 に答える
0

一応、このcreate_tree関数はツリーを再帰的に構築しません。したがって、ノードをゼロレベルに追加するだけで、子は単なる辞書になります。

次の (変更された) コードは (すぐにタイプされてずさんですが)、ツリーの再帰的なビルドを行う必要があります。コードをチェックしませんでしcountたが、正しいと仮定すると、動作するはずです。

class NodeTree(object):
    def __init__(self, name, children):
        self.name = name
        self.children = children

    def count(self):
        # 1 + i children's nodes
        count = 1
        for c in self.children:
            count += c.count()
        return count


def deep_create_tree(d):
    if len(d["children"]) > 0:
        chlds = []
        for i in d["children"]:
            chlds.append(deep_create_tree(i))
    else:
        chlds = []
    n = NodeTree(d["name"], chlds)
    return n


d1 = {'name':'musica', 'children':[{'name':'rock', 'children':[{'name':'origini','children':[]},{'name':'rock&roll','children':[]},{'name':'hard rock', 'children':[]}]},{'name':'jazz', 'children':[{'name':'origini', 'children':[{'name':'1900', 'children':[]}]},{'name':'ragtime', 'children':[]}, {'name':'swing', 'children':[]}]}]}

def scan_tree(tr):
    print tr.name, tr.count()
    for i in tr.children:
        scan_tree(i)

tr = deep_create_tree(d1)
scan_tree(tr)
于 2012-12-04T20:23:14.100 に答える