从Python中的其他文件调用变量

2024-05-19 00:43:51 发布

您现在位置:Python中文网/ 问答频道 /正文

我正在尝试导入文件,情况如下。

file1.py包含:

from file2 import *
username = "steven"

action()

file2.py包含:

def action():
    print username 

但是我无法打印用户名,因为变量'username'是在file1中声明的,而不是在file2中声明的(函数使用变量)

这不是实际的代码,但我可以不在file2的函数中使用file1中的变量吗?


Tags: 文件函数frompyimport声明defusername
3条回答

但是file2.py没有导入file1.py;它怎么会知道username甚至存在?


顺便说一下,我试图避免代码中的循环依赖关系(即模块x导入模块y,模块y导入模块x),因此简单地将file1导入file2可能不是最好的解决方案。

一个更好的方法是不依赖于来自另一个模块的全局变量,只需将名称传递给file2.action()函数:

文件1.py

import file2

username = "steven"

file2.action(username)

文件2.py

def action(name):
    print name 

你想要的,按照你想要的方式,将需要file1导入file2,反之亦然-在一个普通代码中,这将导致循环导入,这显然是行不通的。

但除此之外,如果文件中的函数、类或方法需要了解导入它们的文件上下文中的数据,正确的做法是将这些数据作为函数参数传入。

在您的情况下,您的“操作”功能应该是:

def action(username):
    print username 

在文件1上:

from file2 import action
username = "steven"

action(username)

(您还应该避免使用“import*”,因为它在读取代码时隐藏了名称的来源,因此很难维护)

当然,Python是Python,有一些工作可以做你想做的事情——你可以创建一个特殊的装饰器,用在你导入的函数上,这个装饰器会从另一个文件中重新创建你的函数,并指向当前模块中的全局变量——但那只是愚蠢的。

“OOP”范例允许一个愚蠢的情况,它或多或少像您打算做的事情-方法使用类属性-如果该属性在子类中被重写,方法-甚至是原始的超类方法,将使用新的属性值-如:

class A(object):
    username = ""
    def action(self):
         print self.__class__.username

B类可以在其他文件中定义,因为您打算:

from file2 import A
class B(A):
    username = "Mike"

b = B()
b.action()

现在,为了给你一个完整的答案-这里有一些代码可以做你想做的事情-但是你不做-修改你的函数来获取参数。

我们可以做的是使用一个函数从调用它的地方读取全局变量。这不仅是“不好的实践”—这是错误的,除了一些非常有文档记录的框架,其中“神奇的变量名”用于配置。即使我发现一个框架有这种坏习惯,我也倾向于修补它的函数,以便通过函数调用显式地传递配置。

from inspect import currentframe

def action():
    caller_frame = current_frame(1)
    caller_globals = caller_frame.f_globals
    print caller_globals["username"]

相关问题 更多 >

    热门问题