在类中调用的python函数

时间:2014-03-06 17:54:30

标签: python function oop methods

我在这里有一个有趣的要求。假设我有一个名为Object的类,它有两个方法,func1()和func2()。第二种方法调用func1(),虽然我希望能够改变func1()的函数定义,能够区分从func2()内部调用而不是作为我的Object类的独立方法调用,就像这样:

obj = Object()
obj.func1()

我可以简单地创建两个版本的函数(一个私有方法,用于func2()以及一个公共方法供用户访问;是的我知道在python中确实没有这样的东西私有,但我认为正常的命名约定,我可以说明它只是一个内部函数)。但这需要相当多的冗余,而且如果可能的话,我想尽量避免这种情况。是否有人可以推荐任何机制或策略来做这类事情?

我知道,例如,如果我希望我的整个脚本object.py执行一组代码,如果只作为一个独立的脚本运行(即 - 它没有被导入到另一个脚本的顶部),我会做:

if __name__ == "__main__":
    ...
    code to run if standalone
    ...

我想知道类的方法是否有类似的策略。

3 个答案:

答案 0 :(得分:2)

你也可以像这样使用inspect

import inspect

def func2():
    if inspect.stack()[1][3] == "func1":
        #...do something...
    else:
        #...do something else...

def func1():
    return func2()

有关详细信息,请参阅官方文档:

http://docs.python.org/2/library/inspect.html

答案 1 :(得分:1)

您可以使用sys._getframe()并根据来电者决定做什么。 f_code.co_name返回函数

import sys

class MyClass(object):
    def func1(self):
        frame = sys._getframe(1)
        if frame.f_code.co_name == 'func2':
            print "called from func2"
        else:
            print "called from elsewhere"
    def func2(self):
        self.func1()

c = MyClass()
c.func1()
c.func2()

答案 2 :(得分:1)

通过阅读您的评论,您的实际问题似乎是:您有一个打印输出的方法。如果用户调用代码,那么您希望将输出打印到终端。如果代码是由另一个方法在内部调用的,则不希望打印输出。

@mgilson建议的debug arg是个不错的选择,但是你不希望用户因为某种原因不知道这个选项。

另一种方法是在函数调用期间使函数包装器重定向stdout,然后再恢复它。像这样:

import os
import sys

def suppress_print(f, *args, **kwargs):
    """Call the function f, but print to the null device 
    instead of the screen."""
    old_stdout = sys.stdout
    sys.stdout = open(os.devnull, 'w')

    result = f(*args, **kwargs)

    sys.stdout = old_stdout

    return result

class Foo:

    def bar(self):
        print "This is a test."
        return 42

    def baz(self):
        return suppress_print(self.bar)


foo = Foo()

# this should print to the terminal
foo.bar()

# this shouldn't
foo.baz()

然后,每当你在内部调用函数时,用suppress_print包装它,输出就会被压扁。请注意,这实际上是一个使用上下文管理器的好地方,但我会将其作为进一步的练习...