⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sect12.htm

📁 this is the most basic to learn python
💻 HTM
📖 第 1 页 / 共 3 页
字号:
  <font color=#0000ff>def</font> g(self): <font color=#0000ff>return</font> 'spam'

# So m <font color=#0000ff>is</font> synchronized, f <font color=#0000ff>and</font> g are <font color=#0000ff>not</font>.
c = C()

# On the <font color=#0000ff>class</font> level:
<font color=#0000ff>class</font> D(C):
  <font color=#0000ff>def</font> __init__(self):
    C.__init__(self)
  # You must override an un-synchronized method
  # <font color=#0000ff>in</font> order to synchronize it (just like Java):
  <font color=#0000ff>def</font> f(self): C.f(self)

# Synchronize every (defined) method <font color=#0000ff>in</font> the <font color=#0000ff>class</font>:
synchronize(D)
d = D()
d.f() # Synchronized
d.g() # Not synchronized
d.m() # Synchronized (<font color=#0000ff>in</font> the base <font color=#0000ff>class</font>)

<font color=#0000ff>class</font> E(C):
  <font color=#0000ff>def</font> __init__(self):
    C.__init__(self)
  <font color=#0000ff>def</font> m(self): C.m(self)
  <font color=#0000ff>def</font> g(self): C.g(self)
  <font color=#0000ff>def</font> f(self): C.f(self)
# Only synchronizes m <font color=#0000ff>and</font> g. Note that m ends up
# being doubly-wrapped <font color=#0000ff>in</font> synchronization, which
# doesn't hurt anything but <font color=#0000ff>is</font> inefficient:
synchronize(E, 'm g')
e = E()
e.f()
e.g()
e.m()
#:~</PRE></FONT></BLOCKQUOTE><DIV ALIGN="LEFT"><P><FONT FACE="Georgia">You must call the base class
constructor for <B>Synchronization</B>, but that&#146;s all. In class <B>C</B>
you can see the use of <B>synchronized( )</B> for <B>m</B>, leaving <B>f</B> and
<B>g</B> alone. Class <B>D</B> has all it&#146;s methods synchronized en masse,
and class <B>E</B> uses the convenience function to synchronize <B>m</B> and
<B>g</B>. Note that since <B>m</B> ends up being synchronized twice, it will be
entered and left twice for every call, which isn&#146;t very desirable [there
may be a fix for this]
<A HREF="http://www.mindview.net/Books/TIPython/BackTalk/FindPage/A_310">Add Comment</A></FONT><BR></P></DIV>

<BLOCKQUOTE><FONT SIZE = "+1"><PRE>#: util:Observer.py
# Class support <font color=#0000ff>for</font> <font color=#004488>"observer"</font> pattern.
<font color=#0000ff>from</font> Synchronization <font color=#0000ff>import</font> *

<font color=#0000ff>class</font> Observer:
  <font color=#0000ff>def</font> update(observable, arg):
    '''Called when the observed object <font color=#0000ff>is</font> 
    modified. You call an Observable object's 
    notifyObservers method to notify all the 
    object's observers of the change.'''
    <font color=#0000ff>pass</font>

<font color=#0000ff>class</font> Observable(Synchronization):
  <font color=#0000ff>def</font> __init__(self):
    self.obs = []
    self.changed = 0
    Synchronization.__init__(self)

  <font color=#0000ff>def</font> addObserver(self, observer):
    <font color=#0000ff>if</font> observer <font color=#0000ff>not</font> <font color=#0000ff>in</font> self.obs:
      self.obs.append(observer)

  <font color=#0000ff>def</font> deleteObserver(self, observer):
    self.obs.remove(observer)

  <font color=#0000ff>def</font> notifyObservers(self, arg = None):
    '''If 'changed' indicates that this object 
    has changed, notify all its observers, then 
    call clearChanged(). Each observer has its 
    update() called with two arguments: this 
    observable object <font color=#0000ff>and</font> the generic 'arg'.'''

    self.mutex.acquire()
    <font color=#0000ff>try</font>:
      <font color=#0000ff>if</font> <font color=#0000ff>not</font> self.changed: <font color=#0000ff>return</font>
      # Make a local copy <font color=#0000ff>in</font> case of synchronous
      # additions of observers:
      localArray = self.obs[:]
      self.clearChanged()
    <font color=#0000ff>finally</font>:
      self.mutex.release()
    # Updating <font color=#0000ff>is</font> <font color=#0000ff>not</font> required to be synchronized:
    <font color=#0000ff>for</font> observer <font color=#0000ff>in</font> localArray:
      observer.update(self, arg)

  <font color=#0000ff>def</font> deleteObservers(self): self.obs = []
  <font color=#0000ff>def</font> setChanged(self): self.changed = 1
  <font color=#0000ff>def</font> clearChanged(self): self.changed = 0
  <font color=#0000ff>def</font> hasChanged(self): <font color=#0000ff>return</font> self.changed
  <font color=#0000ff>def</font> countObservers(self): <font color=#0000ff>return</font> len(self.obs)

synchronize(Observable, 
  <font color=#004488>"addObserver deleteObserver deleteObservers "</font> +
  <font color=#004488>"setChanged clearChanged hasChanged "</font> +
  <font color=#004488>"countObservers"</font>)
#:~</PRE></FONT></BLOCKQUOTE><DIV ALIGN="LEFT"><P><FONT FACE="Georgia">Using this library,
</FONT><FONT FACE="Georgia">here is an example of the observer pattern:
<A HREF="http://www.mindview.net/Books/TIPython/BackTalk/FindPage/A_311">Add Comment</A></FONT><BR></P></DIV>

<BLOCKQUOTE><FONT SIZE = "+1"><PRE>#: c10:ObservedFlower.py
# Demonstration of <font color=#004488>"observer"</font> pattern.
<font color=#0000ff>import</font> sys
sys.path += ['../util']
<font color=#0000ff>from</font> Observer <font color=#0000ff>import</font> Observer, Observable

<font color=#0000ff>class</font> Flower:
  <font color=#0000ff>def</font> __init__(self): 
    self.isOpen = 0
    self.openNotifier = Flower.OpenNotifier(self)
    self.closeNotifier= Flower.CloseNotifier(self)
  <font color=#0000ff>def</font> open(self): # Opens its petals
    self.isOpen = 1
    self.openNotifier.notifyObservers()
    self.closeNotifier.open()
  <font color=#0000ff>def</font> close(self): # Closes its petals
    self.isOpen = 0
    self.closeNotifier.notifyObservers()
    self.openNotifier.close()
  <font color=#0000ff>def</font> closing(self): <font color=#0000ff>return</font> self.closeNotifier 

  <font color=#0000ff>class</font> OpenNotifier(Observable):
    <font color=#0000ff>def</font> __init__(self, outer):
      Observable.__init__(self)
      self.outer = outer
      self.alreadyOpen = 0
    <font color=#0000ff>def</font> notifyObservers(self):
      <font color=#0000ff>if</font> self.outer.isOpen <font color=#0000ff>and</font> \
      <font color=#0000ff>not</font> self.alreadyOpen:
        self.setChanged()
        Observable.notifyObservers(self)
        self.alreadyOpen = 1
    <font color=#0000ff>def</font> close(self): 
      self.alreadyOpen = 0 

  <font color=#0000ff>class</font> CloseNotifier(Observable):
    <font color=#0000ff>def</font> __init__(self, outer):
      Observable.__init__(self)
      self.outer = outer
      self.alreadyClosed = 0
    <font color=#0000ff>def</font> notifyObservers(self):
      <font color=#0000ff>if</font> <font color=#0000ff>not</font> self.outer.isOpen <font color=#0000ff>and</font> \
      <font color=#0000ff>not</font> self.alreadyClosed:
        self.setChanged()
        Observable.notifyObservers(self)
        self.alreadyClosed = 1
    <font color=#0000ff>def</font> open(self): 
      alreadyClosed = 0 

<font color=#0000ff>class</font> Bee:
  <font color=#0000ff>def</font> __init__(self, name):
    self.name = name
    self.openObserver = Bee.OpenObserver(self)
    self.closeObserver = Bee.CloseObserver(self)
  # An inner <font color=#0000ff>class</font> <font color=#0000ff>for</font> observing openings:
  <font color=#0000ff>class</font> OpenObserver(Observer):
    <font color=#0000ff>def</font> __init__(self, outer):
      self.outer = outer
    <font color=#0000ff>def</font> update(self, observable, arg):
      <font color=#0000ff>print</font> <font color=#004488>"Bee "</font> + self.outer.name + \
        <font color=#004488>"'s breakfast time!"</font>
  # Another inner <font color=#0000ff>class</font> <font color=#0000ff>for</font> closings:
  <font color=#0000ff>class</font> CloseObserver(Observer):
    <font color=#0000ff>def</font> __init__(self, outer):
      self.outer = outer
    <font color=#0000ff>def</font> update(self, observable, arg):
      <font color=#0000ff>print</font> <font color=#004488>"Bee "</font> + self.outer.name + \
        <font color=#004488>"'s bed time!"</font>

<font color=#0000ff>class</font> Hummingbird:
  <font color=#0000ff>def</font> __init__(self, name): 
    self.name = name
    self.openObserver = \
      Hummingbird.OpenObserver(self)
    self.closeObserver = \
      Hummingbird.CloseObserver(self)
  <font color=#0000ff>class</font> OpenObserver(Observer):
    <font color=#0000ff>def</font> __init__(self, outer):
      self.outer = outer
    <font color=#0000ff>def</font> update(self, observable, arg):
      <font color=#0000ff>print</font> <font color=#004488>"Hummingbird "</font> + self.outer.name + \
        <font color=#004488>"'s breakfast time!"</font>
  <font color=#0000ff>class</font> CloseObserver(Observer):
    <font color=#0000ff>def</font> __init__(self, outer):
      self.outer = outer
    <font color=#0000ff>def</font> update(self, observable, arg):
      <font color=#0000ff>print</font> <font color=#004488>"Hummingbird "</font> + self.outer.name + \
        <font color=#004488>"'s bed time!"</font>

f = Flower()
ba = Bee(<font color=#004488>"Eric"</font>)
bb = Bee(<font color=#004488>"Eric 0.5"</font>)
ha = Hummingbird(<font color=#004488>"A"</font>)
hb = Hummingbird(<font color=#004488>"B"</font>)
f.openNotifier.addObserver(ha.openObserver)
f.openNotifier.addObserver(hb.openObserver)
f.openNotifier.addObserver(ba.openObserver)
f.openNotifier.addObserver(bb.openObserver)
f.closeNotifier.addObserver(ha.closeObserver)
f.closeNotifier.addObserver(hb.closeObserver)
f.closeNotifier.addObserver(ba.closeObserver)
f.closeNotifier.addObserver(bb.closeObserver)
# Hummingbird 2 decides to sleep <font color=#0000ff>in</font>:
f.openNotifier.deleteObserver(hb.openObserver)
# A change that interests observers:
f.open()
f.open() # It's already open, no change.
# Bee 1 doesn't want to go to bed:
f.closeNotifier.deleteObserver(ba.closeObserver)
f.close()
f.close() # It's already closed; no change
f.openNotifier.deleteObservers()
f.open()
f.close()
#:~</PRE></FONT></BLOCKQUOTE><DIV ALIGN="LEFT"><P><FONT FACE="Georgia">The events of interest are that
a <B>Flower</B> can open or close. Because of the use of the inner class idiom,
both these events can be separately observable phenomena. <B>OpenNotifier</B>
and <B>CloseNotifier</B> both inherit <B>Observable</B>, so they have access to
<B>setChanged(&#160;)</B> and can be handed to anything that needs an
<B>Observable</B>.
<A HREF="http://www.mindview.net/Books/TIPython/BackTalk/FindPage/A_312">Add Comment</A></FONT><BR></P></DIV>
<DIV ALIGN="LEFT"><P><FONT FACE="Georgia">The inner class idiom also comes in handy
to define more than one kind of <B>Observer</B>, in <B>Bee</B> and
<B>Hummingbird</B>, since both those classes may want to independently observe
<B>Flower</B> openings and closings. Notice how the inner class idiom provides
something that has most of the benefits of inheritance (the ability to access
the <B>private</B> data in the outer class, for example) without the same
restrictions.
<A HREF="http://www.mindview.net/Books/TIPython/BackTalk/FindPage/A_313">Add Comment</A></FONT><BR></P></DIV>
<DIV ALIGN="LEFT"><P><FONT FACE="Georgia">In <B>main(&#160;)</B>, you can see one
of the prime benefits of the observer pattern: the ability to change behavior at
run time by dynamically registering and un-registering <B>Observer</B>s with
<B>Observable</B>s.
<A HREF="http://www.mindview.net/Books/TIPython/BackTalk/FindPage/A_314">Add Comment</A></FONT><BR></P></DIV>
<DIV ALIGN="LEFT"><P><FONT FACE="Georgia">If you study the code above you&#146;ll
see that <B>OpenNotifier </B>and <B>CloseNotifier</B> use the basic
<B>Observable</B> interface. This means that you could inherit other completely
different <B>Observer</B> classes; the only connection the <B>Observer</B>s have
with <B>Flower</B>s is the <B>Observer</B> interface.
<A HREF="http://www.mindview.net/Books/TIPython/BackTalk/FindPage/A_315">Add Comment</A></FONT><A NAME="_Toc462393596"></A><A NAME="_Toc476705915"></A><A NAME="_Toc534420126"></A><BR></P></DIV>
<A NAME="Heading77"></A><FONT FACE = "Verdana, Tahoma, Arial, Helvetica, Sans"><H2 ALIGN="LEFT">
A visual example of observers</H2></FONT>
<DIV ALIGN="LEFT"><P><FONT FACE="Georgia">The following example is similar to the
<B>ColorBoxes</B> example from Chapter 14 in <I>Thinking in Java, 2<SUP>nd</SUP>
Edition</I>. Boxes are placed in a grid on the screen and each one is
initialized to a random color. In addition, each box <B>implements</B> the
<A NAME="Index24"></A><B>Observer</B> interface and is registered with an
<B>Observable</B> object. When you click on a box, all of the other boxes are
notified that a change has been made because the <B>Observable</B> object
automatically calls each <B>Observer </B>object&#146;s <B>update(&#160;)</B>
method. Inside this method, the box checks to see if it&#146;s adjacent to the
one that was clicked, and if so it changes its color to match the clicked box.
<A HREF="http://www.mindview.net/Books/TIPython/BackTalk/FindPage/A_316">Add Comment</A></FONT><BR></P></DIV>

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -