2015-11-08 128 views
-1

我讀了蟒蛇菜譜第二,在「CHAP 2.13使用C++ - 樣的iostream語法「一個樣品,我試着去了解如何自我作品在超載蟒蛇運算符「<<」作爲C++的iostream

class IOManipulator(object): 
    def __init__(self, function=None): 
     self.function = function 
    def do(self, output): 
     self.function(output) 
def do_endl(stream): 
    stream.output.write('\n') 
    stream.output.flush() 
endl = IOManipulator(do_endl) 
# my understanding, all above is about make a newline and flush sys.stdout, 

class OStream(object): 
    def __init__(self, output=None): 
     if output is None: 
      import sys 
      output = sys.stdout 
     self.output = output 
     self.format = '%s' 
    def __lshift__(self, thing): 
     if isinstance(thing, IOManipulator): 
      thing.do(self) 
      # It make no sense to me, why the function belongs to 
      # another class's instance need call (self) 
     else: 
      self.output.write(self.format % thing) 
      self.format = '%s' # <- is it necessary? seems to be not. 
     return self # <- why return a "self" here? 
     # If comment this line out, 
     # python raise a TypeError when execute to the "<< 1" 
     # TypeError: unsupported operand type(s) for <<: 'NoneType' and 'int' 

def example_main(): 
    cout = OStream() 
    cout << "The average of " << 1 << " and " << 3 << " is " << (1+3)/2 << endl 

if __name__ == '__main__': 
    example_main() 
# emits: 
#> The average of 1 and 3 is 2 

的代碼。「自我」是<__main__.OStream object at 0x7fc28cd92410>,我知道這是ostream的類的實例,也許可以作爲C指針。

+1

'回報self'是因爲你使用所需的''<<在第一次''<<操作的輸出等等... –

+0

時注意如果一個函數錯過了'return'蟒蛇做了'返回None。因此,你看到的錯誤('<<'返回一個'None'和'None << x'沒有定義)。 – Bakuriu

+0

無論如何'返回自我'是**不是**嚴格要求。你必須把'return something'放回去,但'something'可能是別的東西,就像一個新的'OStream'。 – Bakuriu

回答

2

我會回答你提出的問題評論:


if isinstance(thing, IOManipulator): 
    thing.do(self) 
    # It make no sense to me, why the function belongs to 
    # another class's instance need call (self) 

您通過self(輸出流)到thing(這將是一個IOManipulatorendl操作),從而使IOManipulator類可以在執行功能(見下文,IOManipulator.do)輸出流。

def do(self, output): 
    self.function(output) 

混亂的最高金額,第一self在這個片段是不是你傳遞給它的OStreamself!你通過selfthing.do被設置爲output變量。


return self # <- why return a "self" here? 

您這裏返回OStream實例,因此您可以連鎖經營。需要注意的是Python解析行a << b << c(a << b) << c。該(a << b)部件需要以那麼能夠做到就可以了<< c和意義返回其更新自我。如果你對此有何評論return self出來,你最終None << c因爲那麼函數將返回None


self.format 

我不確定什麼作者的意圖與此,似乎沒有必要。行self.output.write(self.format % thing)也可能被寫爲self.output.write(str(thing))


一點題外話:這可能是你能如何實現一個新的運營商的例子,但是這個具體的操作是非常,Python的:它會導致真正的醜陋和混亂的代碼。在現實世界中,嘗試使用語言已有的功能。