Path: csiph.com!usenet.pasdenom.info!dedibox.gegeweb.org!gegeweb.eu!nntpfeed.proxad.net!proxad.net!feeder1-2.proxad.net!usenet-fr.net!nerim.net!novso.com!newsfeed.xs4all.nl!newsfeed3.news.xs4all.nl!xs4all!newsgate.cistron.nl!newsgate.news.xs4all.nl!post.news.xs4all.nl!not-for-mail Return-Path: X-Original-To: python-list@python.org Delivered-To: python-list@mail.python.org X-Spam-Status: OK 0.000 X-Spam-Evidence: '*H*': 1.00; '*S*': 0.00; 'subject:: [': 0.04; '-for': 0.05; 'subject:Python': 0.06; 'class,': 0.07; 'arguments': 0.09; 'classes.': 0.09; 'function:': 0.09; 'received:80.91': 0.09; 'received:80.91.229': 0.09; 'received:gmane.org': 0.09; 'received:list': 0.09; 'subject:method': 0.09; 'subject:set': 0.09; 'violates': 0.09; 'python': 0.11; 'def': 0.12; 'a(object):': 0.16; 'different,': 0.16; 'exactly,': 0.16; 'factory': 0.16; 'inheritance': 0.16; 'objects.': 0.16; 'received:80.91.229.3': 0.16; 'received:plane.gmane.org': 0.16; 'subject:Dev': 0.16; 'substitution': 0.16; 'wrote:': 0.18; 'trying': 0.19; 'subject:] ': 0.20; 'seems': 0.21; '>>>': 0.22; 'separate': 0.22; 'print': 0.22; 'header:User-Agent:1': 0.23; 'either.': 0.24; 'instance,': 0.24; 'class.': 0.26; 'pass': 0.26; 'header:X-Complaints-To:1': 0.27; 'header:In-Reply-To:1': 0.27; 'tried': 0.27; 'function': 0.29; 'ideal': 0.29; 'informative': 0.31; 'names.': 0.31; 'workaround': 0.31; 'class': 0.32; 'plain': 0.33; 'totally': 0.33; 'skip:_ 10': 0.34; 'but': 0.35; 'there': 0.35; 'instances': 0.36; 'received:com.au': 0.36; 'method': 0.36; 'should': 0.36; 'two': 0.37; 'implement': 0.38; 'to:addr:python-list': 0.38; 'to:addr:python.org': 0.39; 'received:org': 0.40; 'called': 0.40; 'simply': 0.61; 'first': 0.61; 'different': 0.65; 'charset:windows-1252': 0.65; "'new'": 0.84; 'received:110': 0.96 X-Injected-Via-Gmane: http://gmane.org/ To: python-list@python.org From: Lie Ryan Subject: Re: [Python-Dev] Dinamically set __call__ method Date: Fri, 14 Nov 2014 02:28:53 +1100 References: <545919B6.7040007@stoneleaf.us> Mime-Version: 1.0 Content-Type: text/plain; charset=windows-1252; format=flowed Content-Transfer-Encoding: 8bit X-Gmane-NNTP-Posting-Host: 110-175-240-90.static.tpgi.com.au User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:31.0) Gecko/20100101 Thunderbird/31.2.0 In-Reply-To: X-BeenThere: python-list@python.org X-Mailman-Version: 2.1.15 Precedence: list List-Id: General discussion list for the Python programming language List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Newsgroups: comp.lang.python Message-ID: Lines: 61 NNTP-Posting-Host: 2001:888:2000:d::a6 X-Trace: 1415892555 news.xs4all.nl 2864 [2001:888:2000:d::a6]:38444 X-Complaints-To: abuse@xs4all.nl Xref: csiph.com comp.lang.python:80690 On 05/11/14 06:15, Roberto Martínez wrote: > > The thing with this is tricky. I need the change in the instance, > not in the class, because I have multiple instances and all of > them must have different implementations of __call__. Why not just use functions with closure if that's what you need? def a(one): two = 'three' def mycall(self): nonlocal two print 'NEW' return mycall Python functions are objects. > The workaround of calling a different method inside __call__ > is not valid for my case because I want to change the *signature* > of the function also -for introspection reasons. This seems like they should be two totally separate classes. If the signature is different, then it violates the substitution principle. If it violates substitution, then there is no reason why they should be of the same class. > This was my first approach, but it is not very informative to the user > and I prefer to have arguments with descriptive names. We have to change > __doc__ too, so this is not an ideal solution for me. > > I tried to implement __getattribute__, but is not called either. :( Or you can use an factory function: def A(p): def xcall(self): return 'X' def ycall(self): return 'Y' class _A(object): __call__ = xcall if p == 'x' else ycall return _A >>> A('x')()(), A('y')()() ('X', 'Y') or plain and simply just use inheritance if you want to pass an isinstance check: class A(object): def __call__(self): print 'OLD' class A1(A): def __call__(self): print 'NEW' What exactly, are you trying to do?