PYTHONPATH环境变量...如何将每个子目录都包含进来?

4 投票
2 回答
8120 浏览
提问于 2025-04-15 15:34

我现在是这样做的:

PYTHONPATH=/home/$USER:/home/$USER/respository:/home/$USER/repository/python-stuff

我该怎么做才能让PYTHONPATH包含所有的子目录呢?

PYTHONPATH = /home/$USER/....and-all-subdirectories

2 个回答

0

我这样做的:

import os
import sys

all_modules = {} #keeps track of the module names

def discoverModules():
    ''' Populates a dictionary holding every module name in the directory tree that this file is run '''    
    global all_modules

    for dirname, dirnames, filenames in os.walk('.'):
        # Advanced usage:
        # editing the 'dirnames' list will stop os.walk() from recursing into there.
        if '.git' in dirnames:
            # don't go into any .git directories.
            dirnames.remove('.git')

        # save path to all subdirectories in the sys.path so we can easily access them:
        for subdirname in dirnames:                    
            name = os.path.join(dirname, subdirname) # complete directory path
            sys.path.append(name) # add every entry to the sys.path for easy import

        # save path to all filenames:
        for filename in filenames:        
            # we want to save all the .py modules, but nothing else:
            if '.py' in filename and '.pyc' not in filename and '__init__' not in filename:
                moduleName = '' #this will hold the final module name

                # If on Mac or Linux system:
                if str(os.name) == 'posix': 
                    for element in dirname.split('\/'): # for each folder in the traversal
                        if element is not '.': # the first element is always a '.', so remove it
                            moduleName += element + '.' # add a '.' between each folder

                # If on windoze system:
                elif str(os.name) == 'nt': 
                    for element in dirname.split('\\'): # for each folder in the traversal
                        if element is not '.': # the first element is always a '.', so remove it
                            moduleName += element + '.' # add a '.' between each folder

                # Important to use rstrip, rather than strip. If you use strip, it will remove '.', 'p', and 'y' instead of just '.py'
                moduleName += filename.rstrip('.py') # finally, add the filename of the module to the name, minus the '.py' extension            
                all_modules[str(filename.rstrip('.py'))] = moduleName # add complete module name to the list of modules
    print 'Discovering Modules...Complete!'
    print 'Discovered ' + str(len(all_modules)) + ' Modules.'
11

一般来说,把一个目录和它的父目录同时放在sys.path里并不是个好主意——前提是子目录里有一个__init__.py文件,这个文件用来标记它是一个包。如果只把父目录放在路径里(而且$PYTHONPATH也是sys.path初始化的一部分),那么就可以通过包来导入子目录里的模块,也就是说只用一个文件系统路径就能避免同一个模块被多次导入的问题。

那么,为什么不在所有需要的子目录里放__init__.py文件,然后使用包导入呢?

虽然我觉得你的这个想法不太好,但其实是可以做到的——在Unix系统中,find命令可以很方便地列出一个目录下的所有子目录,每行一个(用find . -type d),你也可以很容易地把这些行连接起来,比如通过将find的输出传给tr '\n' :

撰写回答