2016-09-21 39 views
2

我是一个相对较新的Python学习者。因此,要通过不同的编码技术,同时,我碰到这样的:使用参数和签名

from inspect import Parameter, Signature 

def make_signature(names): 
    return Signature(Parameter(name, Parameter.POSITIONAL_OR_KEYWORD) for name in names) 

class Structure: 
    list_fields = [] 
    def __init__(self, *args): 
     for name, val in zip(self.list_fields, args): 
      setattr(self, name, val) 

class Stock(Structure): 
    __signature__ = make_signature(['name', 'shares', 'price']) 
    #list_fields = ['name', 'shares', 'price'] 

class Point(Structure): 
    list_fields = ['x', 'y'] 

obj2=Point(20,40) 
obj1=Stock('googl', 100, 8000) 
print(obj1.name) 

我明白Structure类及其与Point类,这是继承Structure类,因此它是__init__方法的整合。但是当我创建Point类的对象时,它不支持位置参数,但Stock类对象确实支持该功能。

  • 任何人都可以请向我解释为什么&这是怎么发生的?
  • 何时使用Parameter,Signature?
  • 这与元编程有什么关系?
  • 更多类似的例子。
  • Parameter函数有什么用途make_signature方法和make_signature方法在做什么?
  • 程序的流程即哪个函数返回给谁,反之亦然。据我所知,Stock班和Point班正在呼叫Structure班,但是什么时候make_signature方法进来?

我想读一些有关的文件,但Signature这些例子都是这样的,并没有太多沉重的东西对我来说我一直迷路回溯这段代码也单证我找不到任何好的解释Python中元编程的文档。

回答

2

任何人都可以请向我解释为什么&这是怎么发生的?

两个类接受位置参数由*argsStructure.__init__决定:

s = Stock('pos_arg1', 'pos_arg2', 'pos_arg3') 
p = Point('pos_arg1', 'pos_arg2', 'pos_arg3') 

不同的是,Stock实际上并不设置任何参数,因为,既然你注释掉list_fieldsStructure.__init__将使用空的Structure.list_fields。这就是为什么在Stock实例上尝试访问name会产生AttributeError

在这两种情况下,list_fields限制可以设置什么参数。对于前面片段中的Point实例,x将等于pos_arg1,而y将等于pos_arg2; pos_arg3实质上是扔了。直到iterables之一耗尽,这是由于zip它建立的元组:

for i, j in zip(['x', 'y'], ['pos_arg1', 'pos_arg2', 'pos_arg3']): 
    print(i, j) 

打印:

x pos_arg1 
y pos_arg2 

当提供一个空列表,它甚至不循环。这是发生了什么,当你初始化Stock,用于Structure.list_fields = []

for i, j in zip([], ['pos_arg1', 'pos_arg2', 'pos_arg3']): 
    print(i, j) 

打印什么所以没有setattr s的将被调用。

何时使用Parameter,Signature?

如果你想支持你的类(或者,在一般情况下可调用)的进一步的反省,你可以一个__signature__属性添加到您的类(如与Stock完成),并把它拾起工具,如inspect.signature ,即:

inspect.signature(Stock) 
Out[16]: <Signature (name, shares, price)> 

inspect.signature(Point) 
Out[17]: <Signature (*args)> 

签名会尝试看看是否对象具有object.__signature__如果是这样构建签名的表示调用时。

此外,你可以bind签名自我,并得到它支持POSITIONAL_OR_KEYWORD的论点。

一般情况下,这只会在极少数情况下作为要求呈现。简而言之:你会知道你是否需要它。

此外,这与元编程有什么关系?

这个具体的例子是不相关的。您可以使用元编程来增强它,就像您将在我将链接的演示文稿中看到的一样。

还有一些这样的例子。

这是太宽泛的请求。但你的例子来自大卫贝兹利的元编程演示,here's the presentation

据我所知Stock函数和Point函数调用Structure类,但make_signature方法在哪里?

两个StockPoint使用Structure.__init__这将填充在list_fields定义的属性的实例字典。

__signature__ = make_signature([...])正在执行当创建类时,Python在遇到它时执行class的主体。 make_signature将被调用,并创建一个Signature对象,并将分配到__signature__即将完成。

+0

您能否介绍一下make_signature方法中的Parameter函数和make_signature方法的用途是什么?你还可以告诉我程序的流程,即哪个功能返回给谁,反之亦然。 – BlackBeard

+0

更新了我的回答@NiladriSekharBasu。注意你的问题已经是5个问题了,你不能不断更新它来请求更多的信息;这就是*新问题。 –