2017-10-22 5 views
0

.mdファイルをファイル内で再帰的に取得しようとしています。これをコンパイルするために、mainモジュールで実行される再帰関数を定義します。`main`モジュールで実行中のNameError

コードは:

import os 
def walk(dirname): 
    for name in os.listdir(dirname): 
     path = os.path.join(dirname, name) 
     if os.path.isfile(path): 
      if '.md' in path: 
       path_list.append(path) 
     else: 
      walk(path) 
    return path_list 
def main(): 
    dir = '/Users/Documents/Diary' 
    path_list = [] 
    path = walk(dir) 

if __name__ == '__main__': 
    main() 

実行し、それが報告されます。

NameError: name 'path_list' is not defined 

をしかし、main()のなしで実行している、それが動作するかどうか:

In [80]: path_list = [] 
    ...: def walk(dirname): 
    ...:  for name in os.listdir(dirname): 
    ...:   path = os.path.join(dirname, name) 
    ...:   if os.path.isfile(path): 
    ...:    if '.md' in path: 
    ...:     path_list.append(path) 
    ...:   else: 
    ...:    walk(path) 
    ...:  return path_list 

出力:

dir = '/Users/Documents/Diary' 
walk(dir) 
Out[81]: 
['/Users/Documents/Diary/py4.1.If_statements.md', 
'/Users/Documents/Diary/pyName_and_object:.md', 
...] 

私はバグを知りません。

答えて

1

第2のオプションでは、グローバル変数としてpath_listが宣言されているため、すべての関数で認識されています。

また、それが必要な唯一の場所であるwalk()関数で宣言することもできます。しかし、コメントされているように、その関数は再帰的に呼び出されるため、結果を集約する代わりに毎回リストをリセットします。

Notes on Python variable scope」でさらにご覧ください。

グローバル変数は、関数の内部および外部からアクセスできます。
ローカル変数は、関数内でのみアクセスできます。
グローバル変数と同じ名前の関数に変数を設定した場合、実際には新しいローカル変数を作成しています。

+0

walk()関数で宣言するにはどうすればいいですか?それは自己を呼び出すために再帰的に呼び出されます。ネストされたディレクトリに出会うと、 'def walk():path_list = []'。 path_listの値は、再帰的に呼び出されるたびにクリアされます。 –

+0

真、その後グローバルな宣言は十分です – VonC

1

ここでの問題は、オブジェクトの範囲の問題です。

main()関数を作成すると、path_listをローカル範囲main()に宣言しています。したがって、walk()の機能には使用できません。

利用可能にするには、後者のようにグローバルにウォーキングまたは宣言するには、path_listを渡す必要があります。現時点では、path_listwalk()の範囲外です。

+0

印象的な、あなたの評判が1であると信じることができない: - –

+0

ありがとう、幸せに役立つ! :) –

0

walk関数では、それが動作している関数なので、path_listを宣言する必要があります。あなたはその関数にあらかじめ宣言されているpath_listがないので、エラーが発生します。

さらに、メイン関数にはpath_listを定義する必要はありません。なぜなら、それが必要ないためです。

グローバルに宣言すると、すべての機能(walk機能を含む)でも使用できます。そのグローバル変数を使用するため、エラーは発生しません。

関連する問題