0

我有一个名为运行while循环命令提示符的类,我正在使用dir()getattr()为命令shell动态创建方法列表。我想返回值,但是从动态调用的方法返回只是退出到主循环,为什么我该如何解决这个问题?

class myClass :
    def __init__(self) :
        self.commands = []
        for x in dir(self) :
                k = getattr( self, x )
                if hasattr(k, '__func__') :
                    self.commands.append(x)
            # strips off __init__ and __main__
            self.commands = self.commands[2:]

    def help(self, args=None) :
        for x in self.commands :

            ####
            #### The issue is here
            print('Command: {}'.format(x))
            f = getattr(self, x)('-h')
            desc = f()
            print('Description: {}'.format(desc))
        ...
        return SomeValue

    def cmd_b(self, args=None) :
        if args == '-h' :
            return 'Some description'
        ...
        return SomeValue

    def cmd_c(self, args=None) :
        ...
        return SomeValue

    def __main__(self) :
        while True :
            command = input(self.ENV['PS1'])
            command += ' '
            command = command.split()
            print(command)
            if len(command) > 1 :
                print(command)
                print(len(command))
                args = command[1:]
                command = command[0]
            else :
                command = command[0]
                args = None

            if command == 'exit'  :
                break

            if command not in dir(self) :
                print("Command `{}` not found".format(command))
                continue
            print(command)
            f = getattr( self, command )(args)
            x = f()
4

1 回答 1

0

getattr和返回值

当您getattr(self, attr)返回相应的对象时,它与直接调用属性相同。例如:

class A:
    def __init__(self):
        self.v = 42
    def func(self):
        return "Remember your towel"

a = A()

以下是等价的

value = a.v
towel = a.func()

value = getattr(a, 'v')
towel = getattr(a, 'func')()

f = getattr(a, 'func')
towel = f()

变量valuetowels42"Remember your towel"在这两种情况下。

这应该回答你的问题。

然而:

代码中的主要问题

然而,代码中的主要问题与getattr.

help方法中,您引用了f从未定义过的函数,因此会引发异常。

但最大的问题在于__main__

except:
    pass

在末尾。你永远不应该这样做:你正在消除错误,使得调试变得非常困难。

如果你想让你的代码对错误有弹性,你应该捕获所有错误并在某处报告它们,例如使用日志消息

import logging

log = logging.getLogger()
# set up the logger

while:
    try:
        func()
    except Exception:
        log.exception('my nice message for the user')

如果您在代码中执行此类操作,则更容易捕获未定义f函数之类的错误。

一些建议:

  • help函数中,您循环遍历所有命令,help包括本身,并打印它们的帮助。您实现帮助的方式,这会导致无限递归。您应该跳过helphelp函数调用。

  • 所有命令都返回None一个字符串。当您按上述方式修复代码时,您会从第 63 行得到很多错误:f()

ps:如果你是从python开始的,可以看看PEP8,官方的python风格指南

于 2017-09-14T07:58:33.987 回答