python NameError:未定义全局名称'__file__'

Posted

技术标签:

【中文标题】python NameError:未定义全局名称\'__file__\'【英文标题】:python NameError: global name '__file__' is not definedpython NameError:未定义全局名称'__file__' 【发布时间】:2013-05-27 11:11:59 【问题描述】:

当我在 python 2.7 中运行此代码时,我收到此错误:

Traceback (most recent call last):
File "C:\Python26\Lib\site-packages\pyutilib.subprocess-3.5.4\setup.py", line 30, in <module>
    long_description = read('README.txt'),
  File "C:\Python26\Lib\site-packages\pyutilib.subprocess-3.5.4\setup.py", line 19, in read
    return open(os.path.join(os.path.dirname(__file__), *rnames)).read()
NameError: global name '__file__' is not defined

代码是:

import os
from setuptools import setup


def read(*rnames):
    return open(os.path.join(os.path.dirname(__file__), *rnames)).read()


setup(name="pyutilib.subprocess",
    version='3.5.4',
    maintainer='William E. Hart',
    maintainer_email='wehart@sandia.gov',
    url = 'https://software.sandia.gov/svn/public/pyutilib/pyutilib.subprocess',
    license = 'BSD',
    platforms = ["any"],
    description = 'PyUtilib utilites for managing subprocesses.',
    long_description = read('README.txt'),
    classifiers = [
        'Development Status :: 4 - Beta',
        'Intended Audience :: End Users/Desktop',
        'License :: OSI Approved :: BSD License',
        'Natural Language :: English',
        'Operating System :: Microsoft :: Windows',
        'Operating System :: Unix',
        'Programming Language :: Python',
        'Programming Language :: Unix Shell',
        'Topic :: Scientific/Engineering :: Mathematics',
        'Topic :: Software Development :: Libraries :: Python Modules'],
      packages=['pyutilib', 'pyutilib.subprocess', 'pyutilib.subprocess.tests'],
      keywords=['utility'],
      namespace_packages=['pyutilib'],
      install_requires=['pyutilib.common', 'pyutilib.services']
      )

【问题讨论】:

【参考方案1】:

当您在 python 交互式 shell 中附加此行 os.path.join(os.path.dirname(__file__)) 时会出现此错误。

Python Shell 没有检测到__file__ 中的当前文件路径,它与您在其中添加此行的filepath 有关

所以你应该在file.py 中写下这行os.path.join(os.path.dirname(__file__))。然后运行python file.py,它可以工作,因为它需要你的文件路径。

【讨论】:

正是我的经验。但是如何让它在 shell 中工作呢? 但是要从脚本运行file.py,例如,您可以将其放在与脚本相同的目录中。所以你需要在运行file.py之前移动到这个目录...所以仍然需要更好的东西。 所以当你 C-c C-p 时 Emacs 使用了一个交互式 shell?蟒蛇壳。有没有办法使用这个 shell,就好像它是一个运行文件的终端一样?运行 shell 有 3 个选项: CMD DEDICATED SHOW 他们中的一个会这样做吗? 所以这不是 setuptools 的答案,因为如果您分发包并按照 pypi.org 的指示使用 twine 构建,那么这个答案都没有帮助,因为 setup.py 将被复制并执行一个 virtualenv 并且不再能够相对找到孤立文件【参考方案2】:

我在使用 PyInstaller 和 Py2exe 时遇到了同样的问题,所以我在 cx-freeze 的常见问题解答中找到了解决方案。

从控制台或作为应用程序使用您的脚本时,下面的函数将为您提供“执行路径”,而不是“实际文件路径”:

print(os.getcwd())
print(sys.argv[0])
print(os.path.dirname(os.path.realpath('__file__')))

来源:http://cx-freeze.readthedocs.org/en/latest/faq.html

您的旧线路(最初的问题):

def read(*rnames):
return open(os.path.join(os.path.dirname(__file__), *rnames)).read()

用以下 sn-p 替换您的代码行。

def find_data_file(filename):
    if getattr(sys, 'frozen', False):
        # The application is frozen
        datadir = os.path.dirname(sys.executable)
    else:
        # The application is not frozen
        # Change this bit to match where you store your data files:
        datadir = os.path.dirname(__file__)

    return os.path.join(datadir, filename)

使用上面的代码,您可以将您的应用程序添加到您的操作系统的路径中,您可以在任何地方执行它,而不会出现您的应用程序无法找到它的数据/配置文件的问题。

用python测试:

3.3.4 2.7.13

【讨论】:

os.path.realpath('__file__') 不起作用,因为它在引号之间。其余的答案都很好【参考方案3】:

我遇到过__file__ 无法按预期工作的情况。但到目前为止,以下内容并没有让我失望:

import inspect
src_file_path = inspect.getfile(lambda: None)

这是最接近 C 语言 __FILE__ 的 Python 类比。

Python 的 __file__ 的行为与 C 的 __FILE__ 有很大不同。 C 版本将为您提供源文件的原始路径。这对于记录错误和了解哪个源文件有错误很有用。

Python 的__file__ 只给你当前正在执行的文件的名字,在日志输出中可能不是很有用。

【讨论】:

当 python 嵌入到另一个应用程序中时也可以使用此方法 我的运气比os.path.dirname(os.path.realpath(...)) 方法好。 这应该是最佳答案。【参考方案4】:

如下更改您的代码!这个对我有用。 `

os.path.dirname(os.path.abspath("__file__"))

【讨论】:

我认为你实际上是在使用os.getcwd(),根据doc,"__file__" 是没有意义的。 为什么会有赞成票?很多人接受了这个,因为它摆脱了一个未处理的异常,他们认为它是正确的?? 这不是一个正确的解决方案的人。它的作用是说你有一个文件名,字面意思是“__file__”,然后你在如果它存在的话!中添加它可能在哪个文件夹中 这显然有效,因为 iPython 无法找到 os.path.dirname( os.path.abspath( os.getcwd() + "\_file_")) 并将其缩短为 os.getcwd() 这段代码没有在相同的上下文中测试...这就是为什么它没有产生相同的错误【参考方案5】:

如果您只需要获取当前工作目录os.getcwd(),只要您没有更改代码中其他地方的工作目录,您就会得到与os.path.dirname(__file__) 相同的内容。 os.getcwd() 也可以在交互模式下工作。

所以 os.path.join(os.path.dirname(__file__)) 变成 os.path.join(os.getcwd())

【讨论】:

这是赢家 这个答案不正确os.path.dirname(__file__)os.getcwd() 报告的内容不同。它给你的是文件的目录名。如果结果与os.getcwd() 匹配,那只是巧合。【参考方案6】:

您使用的是交互式解释器吗?你可以使用

sys.argv[0]

您应该阅读:How do I get the path of the current executed file in Python?

【讨论】:

fd = os.path.dirname(os.path.realpath(file)) nd 打印它打印 .../../folder1/ 但 cwd = os. path.dirname(os.path.realpath(sys.argv[0])) >>> print cwd prints ../../ 这将给出启动 shell 的二进制 python 的路径,而不是当前工作目录 应该是argv[1] 而不是argv[0]【参考方案7】:

如果你从 python shell 运行命令,你会得到这个:

>>> __file__
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
NameError: name '__file__' is not defined

您需要直接执行该文件,将其作为参数传递给python 命令:

$ python somefile.py

在你的情况下,应该是python setup.py install

【讨论】:

【参考方案8】:

如果你通过命令行执行文件,你可以使用这个技巧

import traceback

def get_this_filename():
    try:
        raise NotImplementedError("No error")
    except Exception as e:
        exc_type, exc_value, exc_traceback = sys.exc_info()
        filename = traceback.extract_tb(exc_traceback)[-1].filename
    return filename

这在 UnrealEnginePython 控制台中对我有用,调用 py.exec myfile.py

【讨论】:

【参考方案9】:

如果您正在使用 jupyter notebook,例如:

MODEL_NAME = os.path.basename(文件)[:-3]

---------------------------------------------------------------------------
NameError                                 Traceback (most recent call last)
<ipython-input-10-f391bbbab00d> in <module>
----> 1 MODEL_NAME = os.path.basename(__file__)[:-3]

NameError: name '__file__' is not defined

你应该放置一个'! '前面这样

!MODEL_NAME = os.path.basename(__file__)[:-3]

/bin/bash: -c: line 0: syntax error near unexpected token `('
/bin/bash: -c: line 0: `MODEL_NAME = os.path.basename(__file__)[:-3]'

完成.....

【讨论】:

【参考方案10】:

如果您在 .py 文件中使用代码:使用 os.path.abspath(__file__) 如果您直接在脚本上或在 Jupyter Notebooks 中使用代码: 将 file 放在双引号内。 os.path.abspath("__file__")

【讨论】:

您的答案可以通过额外的支持信息得到改进。请edit 添加更多详细信息,例如引用或文档,以便其他人可以确认您的答案是正确的。你可以找到更多关于如何写好答案的信息in the help center。【参考方案11】:

我遇到了完全相同的问题,并且可能使用了the same tutorial。函数定义:

def read(*rnames):
    return open(os.path.join(os.path.dirname(__file__), *rnames)).read()

有问题,因为os.path.dirname(__file__) 不会返回您需要的内容。尝试将os.path.dirname(__file__) 替换为os.path.dirname(os.path.abspath(__file__))

def read(*rnames):
    return open(os.path.join(os.path.dirname(os.path.abspath(__file__)), *rnames)).read()

我刚刚向 Andrew 发布了当前文档中的代码 sn-p 不起作用,希望它会得到纠正。

【讨论】:

【参考方案12】:

我认为你可以这样做得到你的本地文件路径

if not os.path.isdir(f_dir):
    os.mkdirs(f_dir)

try:
    approot = os.path.dirname(os.path.abspath(__file__))
except NameError:
    approot = os.path.dirname(os.path.abspath(sys.argv[1]))
    my_dir= os.path.join(approot, 'f_dir')

【讨论】:

以上是关于python NameError:未定义全局名称'__file__'的主要内容,如果未能解决你的问题,请参考以下文章

Python:NameError:未定义全局名称“foobar”[重复]

Python XML NameError:未定义全局名称“qn”

NameError:未定义全局名称

NameError:未定义全局名称“unicode” - 在 Python 3 中

python NameError:未定义全局名称'__file__'

NameError:未定义全局名称“reduce”