Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]


Groups > comp.lang.python > #29057 > unrolled thread

Re: Python presentations

Started byJean-Michel Pichavant <jeanmichel@sequans.com>
First post2012-09-13 19:54 +0200
Last post2012-09-15 08:31 +0200
Articles 20 on this page of 23 — 12 participants

Back to article view | Back to comp.lang.python


Contents

  Re: Python presentations Jean-Michel Pichavant <jeanmichel@sequans.com> - 2012-09-13 19:54 +0200
    Re: Python presentations Alister <alister.ware@ntlworld.com> - 2012-09-13 18:18 +0000
    Decorators not worth the effort alex23 <wuwei23@gmail.com> - 2012-09-13 18:58 -0700
      Re: Decorators not worth the effort Cameron Simpson <cs@zip.com.au> - 2012-09-14 12:12 +1000
        Re: Decorators not worth the effort alex23 <wuwei23@gmail.com> - 2012-09-13 20:25 -0700
      Re: Decorators not worth the effort Dieter Maurer <dieter@handshake.de> - 2012-09-14 08:40 +0200
      Re: Decorators not worth the effort Terry Reedy <tjreedy@udel.edu> - 2012-09-14 16:29 -0400
        Re: Decorators not worth the effort Thomas Rachel <nutznetz-0c1b6768-bfa9-48d5-a470-7603bd3aa915@spamschutz.glglgl.de> - 2012-09-15 09:13 +0200
        Re: Decorators not worth the effort alex23 <wuwei23@gmail.com> - 2012-09-16 17:38 -0700
      Re: Decorators not worth the effort Terry Reedy <tjreedy@udel.edu> - 2012-09-14 16:31 -0400
      Re: Decorators not worth the effort Terry Reedy <tjreedy@udel.edu> - 2012-09-14 16:37 -0400
        Re: Decorators not worth the effort 88888 Dihedral <dihedral88888@googlemail.com> - 2012-09-18 16:47 -0700
        Re: Decorators not worth the effort 88888 Dihedral <dihedral88888@googlemail.com> - 2012-09-18 16:47 -0700
      Re: Decorators not worth the effort Terry Reedy <tjreedy@udel.edu> - 2012-09-14 16:33 -0400
      Re: Decorators not worth the effort Ian Kelly <ian.g.kelly@gmail.com> - 2012-09-14 15:16 -0600
        Re: Decorators not worth the effort Steven D'Aprano <steve+comp.lang.python@pearwood.info> - 2012-09-14 23:39 +0000
          Re: Decorators not worth the effort 88888 Dihedral <dihedral88888@googlemail.com> - 2012-09-15 02:45 -0700
            Re: Decorators not worth the effort Dwight Hutto <dwightdhutto@gmail.com> - 2012-09-15 06:04 -0400
              Re: Decorators not worth the effort 88888 Dihedral <dihedral88888@googlemail.com> - 2012-09-15 07:18 -0700
                Re: Decorators not worth the effort Thomas Rachel <nutznetz-0c1b6768-bfa9-48d5-a470-7603bd3aa915@spamschutz.glglgl.de> - 2012-09-18 14:16 +0200
              Re: Decorators not worth the effort 88888 Dihedral <dihedral88888@googlemail.com> - 2012-09-15 07:18 -0700
      Re: Decorators not worth the effort Dwight Hutto <dwightdhutto@gmail.com> - 2012-09-14 23:42 -0400
      Re: Decorators not worth the effort "Dieter Maurer" <dieter@handshake.de> - 2012-09-15 08:31 +0200

Page 1 of 2  [1] 2  Next page →


#29057 — Re: Python presentations

FromJean-Michel Pichavant <jeanmichel@sequans.com>
Date2012-09-13 19:54 +0200
SubjectRe: Python presentations
Message-ID<mailman.623.1347558870.27098.python-list@python.org>
----- Original Message -----
> I have to give a couple of Python presentations in the next weeks,
> and
> I'm still thinking what is the best approach.
> 
> In one presentation for example I will present decorators and context
> managers, and my biggest doubt is how much I should show and explain
> in
> slides and how much in an interactive way (with ipython for example).
> 
> For my experience if I only see code in slides I tend not to believe
> that it works somehow, but also only looking at someone typing can be
> hard to follow and understand what is going on..
> 
> So maybe I should do first slides and then interactive demo, or the
> other way around, showing first how everything works and then
> explaining
> the code with slides.
> 
> What do you think work best in general?
> --
> http://mail.python.org/mailman/listinfo/python-list
> 

I don't like decorators, I think they're not worth the mental effort. So if I were to intend to your presentation, I'd really like you to start demonstrating how decorators are life savers, or with less emphasis, how they can be worth the effort and make me regret all these years without decorators.

Some features in python have this WoW! effect, try to trigger it in front of your audience, that should really help them focus on the subject and be interested in your presentation.

Also try to keep the presentation interactive by asking questions to your audience (unless some of them are already participating), otherwise people will be snoring or texting after 20 minutes.

I think the key for a presentation is to make people interested in the subject and make them realize they can benefit from what you're presenting. Everyone can then google 'python decorators' for the technical and boring details.

I must add that I'm not en experienced presenter, so take my advices for what they're worth (hmm not sure about this grammatical construct :-/ )

JM

[toc] | [next] | [standalone]


#29062

FromAlister <alister.ware@ntlworld.com>
Date2012-09-13 18:18 +0000
Message-ID<Krp4s.222258$5o4.107388@fx23.am4>
In reply to#29057
> Also try to keep the presentation interactive by asking questions to
> your audience (unless some of them are already participating), otherwise
> people will be snoring or texting after 20 minutes.

That is a v good suggestion.
the best presentation I ever attended was one on using an emergency life 
raft presented by a member of the local sailing club (I was a scuba diver 
at the time & our club was lending them some pool time)

The whole presentation consisted of a sequence of questions fired at the 
audience to get them to think the problem trough & arrive at the correct 
sequence of events. Genius

-- 
The best prophet of the future is the past.

[toc] | [prev] | [next] | [standalone]


#29097 — Decorators not worth the effort

Fromalex23 <wuwei23@gmail.com>
Date2012-09-13 18:58 -0700
SubjectDecorators not worth the effort
Message-ID<f7e2ec78-2c4a-402e-9a90-6cf0e7e55a54@c8g2000pbe.googlegroups.com>
In reply to#29057
On Sep 14, 3:54 am, Jean-Michel Pichavant <jeanmic...@sequans.com>
wrote:
> I don't like decorators, I think they're not worth the mental effort.

Because passing a function to a function is a huge cognitive burden?

[toc] | [prev] | [next] | [standalone]


#29101 — Re: Decorators not worth the effort

FromCameron Simpson <cs@zip.com.au>
Date2012-09-14 12:12 +1000
SubjectRe: Decorators not worth the effort
Message-ID<mailman.658.1347588736.27098.python-list@python.org>
In reply to#29097
On 13Sep2012 18:58, alex23 <wuwei23@gmail.com> wrote:
| On Sep 14, 3:54 am, Jean-Michel Pichavant <jeanmic...@sequans.com>
| wrote:
| > I don't like decorators, I think they're not worth the mental effort.
| 
| Because passing a function to a function is a huge cognitive burden?

It is for me when I'm _writing_ the decorator:-) But if I get it right
and name it well I find it dramaticly _decreases_ the cognitive burden
of the code using the decorator...
-- 
Cameron Simpson <cs@zip.com.au>

Observing the first balloon ascent in Paris, [Ben] Franklin heard a scoffer
ask, "What good is it?"  He spoke for a generation of scientists in
his retort, "What good is a newly born infant?" - John F. Kasson

[toc] | [prev] | [next] | [standalone]


#29105 — Re: Decorators not worth the effort

Fromalex23 <wuwei23@gmail.com>
Date2012-09-13 20:25 -0700
SubjectRe: Decorators not worth the effort
Message-ID<50d83c64-033e-498f-a7a4-bafb2f322807@k13g2000pbq.googlegroups.com>
In reply to#29101
On Sep 14, 12:12 pm, Cameron Simpson <c...@zip.com.au> wrote:
> On 13Sep2012 18:58, alex23 <wuwe...@gmail.com> wrote:
> | On Sep 14, 3:54 am, Jean-Michel Pichavant <jeanmic...@sequans.com>| wrote:
> | > I don't like decorators, I think they're not worth the mental effort.
> |
> | Because passing a function to a function is a huge cognitive burden?
>
> It is for me when I'm _writing_ the decorator:-) But if I get it right
> and name it well I find it dramaticly _decreases_ the cognitive burden
> of the code using the decorator...

Okay, I will concede that point :)

[toc] | [prev] | [next] | [standalone]


#29130 — Re: Decorators not worth the effort

FromDieter Maurer <dieter@handshake.de>
Date2012-09-14 08:40 +0200
SubjectRe: Decorators not worth the effort
Message-ID<mailman.678.1347604877.27098.python-list@python.org>
In reply to#29097
> On Sep 14, 3:54 am, Jean-Michel Pichavant <jeanmic...@sequans.com>
> wrote:
>> I don't like decorators, I think they're not worth the mental effort.

Fine.

I like them because they can vastly improve reusability and drastically
reduce redundancies (which I hate). Improved reusability and
reduced redundancies can make applications more readable, easier
to maintain and faster to develop.

[toc] | [prev] | [next] | [standalone]


#29184 — Re: Decorators not worth the effort

FromTerry Reedy <tjreedy@udel.edu>
Date2012-09-14 16:29 -0400
SubjectRe: Decorators not worth the effort
Message-ID<mailman.716.1347654606.27098.python-list@python.org>
In reply to#29097
On 9/13/2012 10:12 PM, Cameron Simpson wrote:
> On 13Sep2012 18:58, alex23 <wuwei23@gmail.com> wrote:
> | On Sep 14, 3:54 am, Jean-Michel Pichavant <jeanmic...@sequans.com>
> | wrote:
> | > I don't like decorators, I think they're not worth the mental effort.
> |
> | Because passing a function to a function is a huge cognitive burden?

For parameterized decorators, there is extra cognitive burden. See below.


> It is for me when I'm _writing_ the decorator:-) But if I get it right
> and name it well I find it dramaticly _decreases_ the cognitive burden
> of the code using the decorator...

For a simple, unparameterized wrapper, the difficulty is entirely in the 
wrapper maker. It must define the final wrapper as a nested function and 
return it*. It is irrelevant whether the wrapper maker is used with 
pre-def decorator syntax or with an explicit post-def call.

*I am here ignoring the option of a class with __call__ method.

For a parameterized wrapper, using decorator syntax requires passing the 
parameter(s) first and the function to be wrapped later. This requires 
currying the wrapper maker with double nesting. The nesting order may 
seem inside-out to some. For most people, this is extra work compared to 
writing a wrapper that accepts the function and parameters together and 
only has a single level of nesting.

In other words

def make_wrapper(func, param):
     def wrapper(*args, **kwds):
         for i in range(param):
             func(*args, **kwds)
     return wrapper

def f(x): print(x)
f = make_wrapper(f, 2)
f('simple')

# is simpler, at least for some people, than the following
# which does essentially the same thing.

def make_outer(param):
     def make_inner(func):
         def wrapper(*args, **kwds):
             for i in range(param):
                 func(*args, **kwds)
         return wrapper
     return make_inner

@make_outer(2)
def f(x): print(x)
f('complex')

Is the gain of not repeating the wrapped function name twice in the 
post-def wrapping call, and the gain of knowing the function will be 
wrapped before reading the def, worth the pain of currying the wrapper 
maker?

-- 
Terry Jan Reedy

[toc] | [prev] | [next] | [standalone]


#29210 — Re: Decorators not worth the effort

FromThomas Rachel <nutznetz-0c1b6768-bfa9-48d5-a470-7603bd3aa915@spamschutz.glglgl.de>
Date2012-09-15 09:13 +0200
SubjectRe: Decorators not worth the effort
Message-ID<k319qh$4n4$1@r03.glglgl.gl>
In reply to#29184
[Sorry, my Firefox destroyed the indent...

Am 14.09.2012 22:29 schrieb Terry Reedy:

> In other words
>
> def make_wrapper(func, param):
> def wrapper(*args, **kwds):
> for i in range(param):
> func(*args, **kwds)
> return wrapper
>
> def f(x): print(x)
> f = make_wrapper(f, 2)
> f('simple')
>
> # is simpler, at least for some people, than the following
> # which does essentially the same thing.
>
> def make_outer(param):
> def make_inner(func):
> def wrapper(*args, **kwds):
> for i in range(param):
> func(*args, **kwds)
> return wrapper
> return make_inner
>
> @make_outer(2)
> def f(x): print(x)
> f('complex')

For this case, my mydeco.py which I use quite often contains a

def indirdeco(ind):
     # Update both the outer as well as the inner wrapper.
     # If we knew the inner one was to be updated with something
     # from *a, **k, we could do it. But not this way...
     @functools.wraps(ind)
     def outer(*a, **k):
         @functools.wraps(ind)
         def inner(f):
             return ind(f, *a, **k)
         return inner
     return outer

so I can do

@indirdeco
def make_wrapper(func, param):
     @functools.wraps(func)
     def wrapper(*args, **kwds):
         for i in range(param):
             func(*args, **kwds)
     return wrapper

and then nevertheless

@make_wrapper(2)
def f(x): print(x)

BTW, I also have a "meta-decorator" for the other direction:

def wrapfunction(mighty):
     """Wrap a function taking (f, *a, **k) and replace it with a
     function taking (f) and returning a function taking (*a, **k) which
     calls our decorated function.
     Other direction than indirdeco."""
     @functools.wraps(mighty)
     def wrapped_outer(inner):
         @functools.wraps(inner)
         def wrapped_inner(*a, **k):
             return mighty(inner, *a, **k)
         wrapped_inner.func = inner # keep the wrapped function
         wrapped_inner.wrapper = mighty # and the replacement
         return wrapped_inner
     wrapped_outer.func = mighty # keep this as well
     return wrapped_outer

With this, a

@wrapfunction
def twice(func, *a, **k):
     return func(*a, **k), func(*a, **k)

can be used with

@twice
def f(x): print (x); return x

very nicely.


Thomas

[toc] | [prev] | [next] | [standalone]


#29351 — Re: Decorators not worth the effort

Fromalex23 <wuwei23@gmail.com>
Date2012-09-16 17:38 -0700
SubjectRe: Decorators not worth the effort
Message-ID<f6cda94f-83ee-4110-832f-1f74e21c58ee@q9g2000pbo.googlegroups.com>
In reply to#29184
On Sep 15, 6:30 am, Terry Reedy <tjre...@udel.edu> wrote:
> > On 13Sep2012 18:58, alex23 <wuwe...@gmail.com> wrote:
> > | On Sep 14, 3:54 am, Jean-Michel Pichavant <jeanmic...@sequans.com>
> > | wrote:
> > | > I don't like decorators, I think they're not worth the mental effort.
> > |
> > | Because passing a function to a function is a huge cognitive burden?
>
> For parameterized decorators, there is extra cognitive burden. See below.

I do regret my initial criticism, for exactly this reason.

[toc] | [prev] | [next] | [standalone]


#29185 — Re: Decorators not worth the effort

FromTerry Reedy <tjreedy@udel.edu>
Date2012-09-14 16:31 -0400
SubjectRe: Decorators not worth the effort
Message-ID<mailman.717.1347654906.27098.python-list@python.org>
In reply to#29097
On 9/14/2012 5:28 AM, Jean-Michel Pichavant wrote:
> Decorators are very popular so I kinda already know that the fault is mine. Now to the reason why I have troubles writing them, I don't know. Every time I did use decorators, I spent way too much time writing it (and debugging it).


-- 
Terry Jan Reedy

[toc] | [prev] | [next] | [standalone]


#29186 — Re: Decorators not worth the effort

FromTerry Reedy <tjreedy@udel.edu>
Date2012-09-14 16:37 -0400
SubjectRe: Decorators not worth the effort
Message-ID<mailman.718.1347655202.27098.python-list@python.org>
In reply to#29097
2nd try, hit send button by mistake before

On 9/14/2012 5:28 AM, Jean-Michel Pichavant wrote:

> Decorators are very popular so I kinda already know that the fault is
> mine. Now to the reason why I have troubles writing them, I don't
> know. Every time I did use decorators, I spent way too much time
> writing it (and debugging it).

You are writing parameterized decorators, which require inverted 
currying of the wrapper maker. Perhaps that is why you have trouble. As 
I showed in response to Cameron, it may be easier to avoid that by using 
a traditional post-def wrapping call instead of decorator syntax.

-- 
Terry Jan Reedy

[toc] | [prev] | [next] | [standalone]


#29455 — Re: Decorators not worth the effort

From88888 Dihedral <dihedral88888@googlemail.com>
Date2012-09-18 16:47 -0700
SubjectRe: Decorators not worth the effort
Message-ID<5995c4c4-42f0-4af1-9154-eb3378230cf9@googlegroups.com>
In reply to#29186
Terry Reedy於 2012年9月15日星期六UTC+8上午4時40分32秒寫道:
> 2nd try, hit send button by mistake before
> 
> 
> 
> On 9/14/2012 5:28 AM, Jean-Michel Pichavant wrote:
> 
> 
> 
> > Decorators are very popular so I kinda already know that the fault is
> 
> > mine. Now to the reason why I have troubles writing them, I don't
> 
> > know. Every time I did use decorators, I spent way too much time
> 
> > writing it (and debugging it).
> 
> 
> 
> You are writing parameterized decorators, which require inverted 
> 
> currying of the wrapper maker. Perhaps that is why you have trouble. As 
> 
> I showed in response to Cameron, it may be easier to avoid that by using 
> 
> a traditional post-def wrapping call instead of decorator syntax.
> 
> 
>  
> -- 
> 
> Terry Jan Reedy

I'll give another example to show the decorators in python in
versions above 2.4 .

# a general function with the variable input : def  fname( *argc,  **argn)
# a deco is a mapping from an input  funtion to another  function

def deco( fn, *list_in, **dict_in): # use list_in and dict_in to modify fn
    """ deco wrapper """ # deco.__doc__ 

    #print list_in, dict_in, " in the deco"
 
    def wrapper( fn, *argc, **argan): # to be returned as a function
       # do things one wants before calling fn 
       result=fn(*argc, **argn)  # call the original, save the result
       # do things after calling fn   
       return result 
    # enhance the  wrapper and get info of fn
    wrapper.__doc__=fn.__doc__
    # enhance wrapper with result, fn, list_in, dict_in
    #....
     return wrapper

def f1():
   """ doc of f1"""
   print "inside f1"

f2=deco(f1, 2,3,4,5,6, MSG="deco f1 to f2")

f2() # invoke the decorated function from f1


# For a deco maps a deco to another deco  can be done similarly

[toc] | [prev] | [next] | [standalone]


#29456 — Re: Decorators not worth the effort

From88888 Dihedral <dihedral88888@googlemail.com>
Date2012-09-18 16:47 -0700
SubjectRe: Decorators not worth the effort
Message-ID<mailman.894.1348012073.27098.python-list@python.org>
In reply to#29186
Terry Reedy於 2012年9月15日星期六UTC+8上午4時40分32秒寫道:
> 2nd try, hit send button by mistake before
> 
> 
> 
> On 9/14/2012 5:28 AM, Jean-Michel Pichavant wrote:
> 
> 
> 
> > Decorators are very popular so I kinda already know that the fault is
> 
> > mine. Now to the reason why I have troubles writing them, I don't
> 
> > know. Every time I did use decorators, I spent way too much time
> 
> > writing it (and debugging it).
> 
> 
> 
> You are writing parameterized decorators, which require inverted 
> 
> currying of the wrapper maker. Perhaps that is why you have trouble. As 
> 
> I showed in response to Cameron, it may be easier to avoid that by using 
> 
> a traditional post-def wrapping call instead of decorator syntax.
> 
> 
>  
> -- 
> 
> Terry Jan Reedy

I'll give another example to show the decorators in python in
versions above 2.4 .

# a general function with the variable input : def  fname( *argc,  **argn)
# a deco is a mapping from an input  funtion to another  function

def deco( fn, *list_in, **dict_in): # use list_in and dict_in to modify fn
    """ deco wrapper """ # deco.__doc__ 

    #print list_in, dict_in, " in the deco"
 
    def wrapper( fn, *argc, **argan): # to be returned as a function
       # do things one wants before calling fn 
       result=fn(*argc, **argn)  # call the original, save the result
       # do things after calling fn   
       return result 
    # enhance the  wrapper and get info of fn
    wrapper.__doc__=fn.__doc__
    # enhance wrapper with result, fn, list_in, dict_in
    #....
     return wrapper

def f1():
   """ doc of f1"""
   print "inside f1"

f2=deco(f1, 2,3,4,5,6, MSG="deco f1 to f2")

f2() # invoke the decorated function from f1


# For a deco maps a deco to another deco  can be done similarly

[toc] | [prev] | [next] | [standalone]


#29188 — Re: Decorators not worth the effort

FromTerry Reedy <tjreedy@udel.edu>
Date2012-09-14 16:33 -0400
SubjectRe: Decorators not worth the effort
Message-ID<mailman.720.1347655802.27098.python-list@python.org>
In reply to#29097
On 9/14/2012 4:29 PM, Terry Reedy wrote:
> On 9/13/2012 10:12 PM, Cameron Simpson wrote:
>> On 13Sep2012 18:58, alex23 <wuwei23@gmail.com> wrote:
>> | On Sep 14, 3:54 am, Jean-Michel Pichavant <jeanmic...@sequans.com>
>> | wrote:
>> | > I don't like decorators, I think they're not worth the mental effort.
>> |
>> | Because passing a function to a function is a huge cognitive burden?
>
> For parameterized decorators, there is extra cognitive burden. See below.
>
>
>> It is for me when I'm _writing_ the decorator:-) But if I get it right
>> and name it well I find it dramaticly _decreases_ the cognitive burden
>> of the code using the decorator...
>
> For a simple, unparameterized wrapper, the difficulty is entirely in the
> wrapper maker. It must define the final wrapper as a nested function and
> return it*. It is irrelevant whether the wrapper maker is used with
> pre-def decorator syntax or with an explicit post-def call.
>
> *I am here ignoring the option of a class with __call__ method.
>
> For a parameterized wrapper, using decorator syntax requires passing the
> parameter(s) first and the function to be wrapped later. This requires
> currying the wrapper maker with double nesting. The nesting order may
> seem inside-out to some. For most people, this is extra work compared to
> writing a wrapper that accepts the function and parameters together and
> only has a single level of nesting.
>
> In other words
>
> def make_wrapper(func, param):
>      def wrapper(*args, **kwds):
>          for i in range(param):
>              func(*args, **kwds)
>      return wrapper
>
> def f(x): print(x)
> f = make_wrapper(f, 2)
> f('simple')
>
> # is simpler, at least for some people, than the following
> # which does essentially the same thing.
>
> def make_outer(param):
>      def make_inner(func):
>          def wrapper(*args, **kwds):
>              for i in range(param):
>                  func(*args, **kwds)
>          return wrapper
>      return make_inner
>
> @make_outer(2)
> def f(x): print(x)
> f('complex')
>
> Is the gain of not repeating the wrapped function name twice in the
> post-def wrapping call, and the gain of knowing the function will be
> wrapped before reading the def, worth the pain of currying the wrapper
> maker?
>


-- 
Terry Jan Reedy

[toc] | [prev] | [next] | [standalone]


#29190 — Re: Decorators not worth the effort

FromIan Kelly <ian.g.kelly@gmail.com>
Date2012-09-14 15:16 -0600
SubjectRe: Decorators not worth the effort
Message-ID<mailman.722.1347657439.27098.python-list@python.org>
In reply to#29097
On Fri, Sep 14, 2012 at 2:29 PM, Terry Reedy <tjreedy@udel.edu> wrote:
> For a simple, unparameterized wrapper, the difficulty is entirely in the
> wrapper maker. It must define the final wrapper as a nested function and
> return it*. It is irrelevant whether the wrapper maker is used with pre-def
> decorator syntax or with an explicit post-def call.
>
> *I am here ignoring the option of a class with __call__ method.
>
> For a parameterized wrapper, using decorator syntax requires passing the
> parameter(s) first and the function to be wrapped later. This requires
> currying the wrapper maker with double nesting. The nesting order may seem
> inside-out to some. For most people, this is extra work compared to writing
> a wrapper that accepts the function and parameters together and only has a
> single level of nesting.
>
> In other words
>
> def make_wrapper(func, param):
>     def wrapper(*args, **kwds):
>         for i in range(param):
>             func(*args, **kwds)
>     return wrapper
>
> def f(x): print(x)
> f = make_wrapper(f, 2)
> f('simple')
>
> # is simpler, at least for some people, than the following
> # which does essentially the same thing.
>
> def make_outer(param):
>     def make_inner(func):
>         def wrapper(*args, **kwds):
>             for i in range(param):
>                 func(*args, **kwds)
>         return wrapper
>     return make_inner
>
> @make_outer(2)
> def f(x): print(x)
> f('complex')
>
> Is the gain of not repeating the wrapped function name twice in the post-def
> wrapping call, and the gain of knowing the function will be wrapped before
> reading the def, worth the pain of currying the wrapper maker?

If only there were a conceptually simpler way to do this.  Actually,
there is.  I give you: metadecorators!

First, the simple, non-parameterized case:

from functools import partial

def make_wrapper(wrapper):
    return lambda wrapped: partial(wrapper, wrapped)

With that simple function buried in a utility module somewhere, we can do:

@make_wrapper
def simple_decorator(func, *args, **kwargs):
    do_stuff()
    result = func(*args, **kwargs)
    do_more_stuff()
    return result

Which I think is certainly easier to understand than the nested
functions approach.  Parameterized decorators are not much more
difficult this way.  This function:

def make_parameterized_wrapper(wrapper):
    return lambda *params: lambda wrapped: partial(wrapper, wrapped, params)

enables us to write:

@make_parameterized_wrapper
def complex_decorator(func, (param1, param2, param3), *args, **kwargs):
    do_stuff(param1, param2)
    result = func(*args, **kwargs)
    do_more_stuff(param2, param3)
    return result

And now we have a fancy parameterized decorator that again requires no
thinking about nested functions at all.  Sadly, that last bit of
syntax will only work in Python 2; tuple parameter unpacking was
removed in Python 3.  It's not a complicated upgrade path, however:

@make_parameterized_wrapper
def complex_decorator(func, params, *args, **kwargs):
    (param1, param2, param3) = params
    do_stuff(param1, param2)
    result = func(*args, **kwargs)
    do_more_stuff(param2, param3)
    return result

Cheers,
Ian

[toc] | [prev] | [next] | [standalone]


#29195 — Re: Decorators not worth the effort

FromSteven D'Aprano <steve+comp.lang.python@pearwood.info>
Date2012-09-14 23:39 +0000
SubjectRe: Decorators not worth the effort
Message-ID<5053c030$0$29981$c3e8da3$5496439d@news.astraweb.com>
In reply to#29190
On Fri, 14 Sep 2012 15:16:47 -0600, Ian Kelly wrote:

> If only there were a conceptually simpler way to do this.  Actually,
> there is.  I give you: metadecorators!
[code snipped but shown below]
> Which I think is certainly easier to understand than the nested
> functions approach.

Maybe for you, but to me it is a big ball of mud. I have no idea how this 
is supposed to work! At a quick glance, I would have sworn that it 
*can't* work, since simple_decorator needs to see multiple arguments but 
only receives one, the function to be decorated. And yet it does work:

py> from functools import partial
py> def make_wrapper(wrapper):
...     return lambda wrapped: partial(wrapper, wrapped)
...
py> @make_wrapper
... def simple_decorator(func, *args, **kwargs):
...     print "Entering decorated function"
...     result = func(*args, **kwargs)
...     print "Exiting decorated function"
...     return result
...
py> @simple_decorator
... def my_function(a, b, c):
...     """Doc string"""
...     return a+b+c
...
py> my_function(1, 2, 3)
Entering decorated function
Exiting decorated function
6

So to me, this is far more magical than nested functions. If I saw this 
in t requires me to hunt through your library for the "simple function 
buried in a utility module somewhere" (your words), instead of seeing 
everything needed in a single decorator factory function. It requires 
that I understand how partial works, which in my opinion is quite tricky. 
(I never remember how it works or which arguments get curried.)

And the end result is that the decorated function is less debugging-
friendly than I demand: it is an anonymous partial object instead of a 
named function, and the doc string is lost. And it is far from clear to 
me how to modify your recipe to use functools.wraps in order to keep the 
name and docstring, or even whether I *can* use functools.wraps.

I dare say I could answer all those questions with some experimentation 
and research. But I don't think that your "metadecorator" using partial 
is *inherently* more understandable than the standard decorator approach:

def simple_decorator2(func):
    @functools.wraps(func)
    def inner(*args, **kwargs):
        print "Entering decorated function"
        result = func(*args, **kwargs)
        print "Exiting decorated function"
        return result
    return inner

This is no more complex than yours, and it keeps the function name and 
docstring.


> Parameterized decorators are not much more
> difficult this way.  This function:
[snip code]
> And now we have a fancy parameterized decorator that again requires no
> thinking about nested functions at all.

Again, at the cost of throwing away the function name and docstring.

I realise that a lot of this boils down to personal preference, but I 
just don't think that nested functions are necessarily that hard to 
grasp, so I prefer to see as much of the decorator logic to be in one 
place (a nested decorator function) rather than scattered across two 
separate decorators plus partial.




-- 
Steven

[toc] | [prev] | [next] | [standalone]


#29215 — Re: Decorators not worth the effort

From88888 Dihedral <dihedral88888@googlemail.com>
Date2012-09-15 02:45 -0700
SubjectRe: Decorators not worth the effort
Message-ID<a6de2f24-c9af-4193-8ce3-63743fe424be@googlegroups.com>
In reply to#29195
Steven D'Aprano於 2012年9月15日星期六UTC+8上午7時39分28秒寫道:
> On Fri, 14 Sep 2012 15:16:47 -0600, Ian Kelly wrote:
> 
> 
> 
> > If only there were a conceptually simpler way to do this.  Actually,
> 
> > there is.  I give you: metadecorators!
> 
> [code snipped but shown below]
> 
> > Which I think is certainly easier to understand than the nested
> 
> > functions approach.
> 
> 
> 
> Maybe for you, but to me it is a big ball of mud. I have no idea how this 
> 
> is supposed to work! At a quick glance, I would have sworn that it 
> 
> *can't* work, since simple_decorator needs to see multiple arguments but 
> 
> only receives one, the function to be decorated. And yet it does work:
> 
> 
> 
> py> from functools import partial
> 
> py> def make_wrapper(wrapper):
> 
> ...     return lambda wrapped: partial(wrapper, wrapped)
> 
> ...
> 
> py> @make_wrapper
> 
> ... def simple_decorator(func, *args, **kwargs):
> 
> ...     print "Entering decorated function"
> 
> ...     result = func(*args, **kwargs)
> 
> ...     print "Exiting decorated function"
> 
> ...     return result
> 
> ...
> 
> py> @simple_decorator
> 
> ... def my_function(a, b, c):
> 
> ...     """Doc string"""
> 
> ...     return a+b+c
> 
> ...
> 
> py> my_function(1, 2, 3)
> 
> Entering decorated function
> 
> Exiting decorated function
> 
> 6
> 
> 
> 
> So to me, this is far more magical than nested functions. If I saw this 
> 
> in t requires me to hunt through your library for the "simple function 
> 
> buried in a utility module somewhere" (your words), instead of seeing 
> 
> everything needed in a single decorator factory function. It requires 
> 
> that I understand how partial works, which in my opinion is quite tricky. 
> 
> (I never remember how it works or which arguments get curried.)
> 
> 
> 
> And the end result is that the decorated function is less debugging-
> 
> friendly than I demand: it is an anonymous partial object instead of a 
> 
> named function, and the doc string is lost. And it is far from clear to 
> 
> me how to modify your recipe to use functools.wraps in order to keep the 
> 
> name and docstring, or even whether I *can* use functools.wraps.
> 
> 
> 
> I dare say I could answer all those questions with some experimentation 
> 
> and research. But I don't think that your "metadecorator" using partial 
> 
> is *inherently* more understandable than the standard decorator approach:
> 
> 
> 
> def simple_decorator2(func):
> 
>     @functools.wraps(func)
> 
>     def inner(*args, **kwargs):
> 
>         print "Entering decorated function"
> 
>         result = func(*args, **kwargs)
> 
>         print "Exiting decorated function"
> 
>         return result
> 
>     return inner
> 
> 
> 
> This is no more complex than yours, and it keeps the function name and 
> 
> docstring.
> 
> 
> 
> 
> 
> > Parameterized decorators are not much more
> 
> > difficult this way.  This function:
> 
> [snip code]
> 
> > And now we have a fancy parameterized decorator that again requires no
> 
> > thinking about nested functions at all.
> 
> 
> 
> Again, at the cost of throwing away the function name and docstring.
> 
> 
> 
> I realise that a lot of this boils down to personal preference, but I 
> 
> just don't think that nested functions are necessarily that hard to 
> 
> grasp, so I prefer to see as much of the decorator logic to be in one 
> 
> place (a nested decorator function) rather than scattered across two 
> 
> separate decorators plus partial.
> 
> 
> 
> 
> 
> 
> 
> 
> 
> -- 
> 
> Steven
 

I think the problem is not in the replaced f.__doc__.

 
def MIGHT_FAIL(f, MSG, *k, **h):
     
# use MSG to determine whether  to invoke f or not 
# and do an error catch  here
     ....
     def innner(f): .....
     ......
     # get the right info of  f here for any trapped error   
     #return inner, result
     return inner
          
    

[toc] | [prev] | [next] | [standalone]


#29216 — Re: Decorators not worth the effort

FromDwight Hutto <dwightdhutto@gmail.com>
Date2012-09-15 06:04 -0400
SubjectRe: Decorators not worth the effort
Message-ID<mailman.742.1347703468.27098.python-list@python.org>
In reply to#29215
On Sat, Sep 15, 2012 at 5:45 AM, 88888 Dihedral
<dihedral88888@googlemail.com> wrote:
> Steven D'Aprano於 2012年9月15日星期六UTC+8上午7時39分28秒寫道:
>> On Fri, 14 Sep 2012 15:16:47 -0600, Ian Kelly wrote:
>>
>>
>>
>> > If only there were a conceptually simpler way to do this.  Actually,
>>
>> > there is.  I give you: muman than humanetadecorators!
>>
>> [code snipped but shown below]
>>
>> > Which I think is certainly easier to understand than the nested
>>
>> > functions approach.
>>
>>
>>
>> Maybe for you, but to me it is a big ball of mud. I have no idea how this
>>
>> is supposed to work! At a quick glance, I would have sworn that it
>>
>> *can't* work, since simple_decorator needs to see multiple arguments but
>>
>> only receives one, the function to be decorated. And yet it does work:
>>
>>
>>
>> py> from functools import partial
>>
>> py> def make_wrapper(wrapper):
>>
>> ...     return lambda wrapped: partial(wrapper, wrapped)
>>
>> ...
>>
>> py> @make_wrapper
>>
>> ... def simple_decorator(func, *args, **kwargs):
>>
>> ...     print "Entering decorated function"
>>
>> ...     result = func(*args, **kwargs)
>>
>> ...     print "Exiting decorated function"
>>
>> ...     return result
>>
>> ...
>>
>> py> @simple_decorator
>>
>> ... def my_function(a, b, c):
>>
>> ...     """Doc string"""
>>
>> ...     return a+b+c
>>
>> ...
>>
>> py> my_function(1, 2, 3)
>>
>> Entering decorated function
>>
>> Exiting decorated function
>>
>> 6
>>
>>
>>
>> So to me, this is far more magical than nested functions. If I saw this
>>
>> in t requires me to hunt through your library for the "simple function
>>
>> buried in a utility module somewhere" (your words), instead of seeing
>>
>> everything needed in a single decorator factory function. It requires
>>
>> that I understand how partial works, which in my opinion is quite tricky.
>>
>> (I never remember how it works or which arguments get curried.)
>>
>>
>>
>> And the end result is that the decorated function is less debugging-
>>
>> friendly than I demand: it is an anonymous partial object instead of a
>>
>> named function, and the doc string is lost. And it is far from clear to
>>
>> me how to modify your recipe to use functools.wraps in order to keep the
>>
>> name and docstring, or even whether I *can* use functools.wraps.
>>
>>
>>
>> I dare say I could answer all those questions with some experimentation
>>
>> and research. But I don't think that your "metadecorator" using partial
>>
>> is *inherently* more understandable than the standard decorator approach:
>>
>>
>>
>> def simple_decorator2(func):
>>
>>     @functools.wraps(func)
>>
>>     def inner(*args, **kwargs):
>>
>>         print "Entering decorated function"
>>
>>         result = func(*args, **kwargs)
>>
>>         print "Exiting decorated function"
>>
>>         return result
>>
>>     return inner
>>
>>
>>
>> This is no more complex than yours, and it keeps the function name and
>>
>> docstring.
>>
>>
>>
>>
>>
>> > Parameterized decorators are not much more
>>
>> > difficult this way.  This function:
>>
>> [snip code]
>>
>> > And now we have a fancy parameterized decorator that again requires no
>>
>> > thinking about nested functions at all.
>>
>>
>>
>> Again, at the cost of throwing away the function name and docstring.
>>
>>
>>
>> I realise that a lot of this boils down to personal preference, but I
>>
>> just don't think that nested functions are necessarily that hard to
>>
>> grasp, so I prefer to see as much of the decorator logic to be in one
>>
>> place (a nested decorator function) rather than scattered across two
>>
>> separate decorators plus partial.

Like chi fu, allow decorators to evolve upon themselves. Like simple
moves flow through water and allow memorization of activity through
evidence of existence.


-- 
Best Regards,
David Hutto
CEO: http://www.hitwebdevelopment.com

[toc] | [prev] | [next] | [standalone]


#29229 — Re: Decorators not worth the effort

From88888 Dihedral <dihedral88888@googlemail.com>
Date2012-09-15 07:18 -0700
SubjectRe: Decorators not worth the effort
Message-ID<331d26cd-8bb9-4994-9adf-fa2462bcfd6e@googlegroups.com>
In reply to#29216
David Hutto於 2012年9月15日星期六UTC+8下午6時04分28秒寫道:
> On Sat, Sep 15, 2012 at 5:45 AM, 88888 Dihedral
> 
> <dihedral88888@googlemail.com> wrote:
> 
> > Steven D'Aprano於 2012年9月15日星期六UTC+8上午7時39分28秒寫道:
> 
> >> On Fri, 14 Sep 2012 15:16:47 -0600, Ian Kelly wrote:
> 
> >>
> 
> >>
> 
> >>
> 
> >> > If only there were a conceptually simpler way to do this.  Actually,
> 
> >>
> 
> >> > there is.  I give you: muman than humanetadecorators!
> 
> >>
> 
> >> [code snipped but shown below]
> 
> >>
> 
> >> > Which I think is certainly easier to understand than the nested
> 
> >>
> 
> >> > functions approach.
> 
> >>
> 
> >>
> 
> >>
> 
> >> Maybe for you, but to me it is a big ball of mud. I have no idea how this
> 
> >>
> 
> >> is supposed to work! At a quick glance, I would have sworn that it
> 
> >>
> 
> >> *can't* work, since simple_decorator needs to see multiple arguments but
> 
> >>
> 
> >> only receives one, the function to be decorated. And yet it does work:
> 
> >>
> 
> >>
> 
> >>
> 
> >> py> from functools import partial
> 
> >>
> 
> >> py> def make_wrapper(wrapper):
> 
> >>
> 
> >> ...     return lambda wrapped: partial(wrapper, wrapped)
> 
> >>
> 
> >> ...
> 
> >>
> 
> >> py> @make_wrapper
> 
> >>
> 
> >> ... def simple_decorator(func, *args, **kwargs):
> 
> >>
> 
> >> ...     print "Entering decorated function"
> 
> >>
> 
> >> ...     result = func(*args, **kwargs)
> 
> >>
> 
> >> ...     print "Exiting decorated function"
> 
> >>
> 
> >> ...     return result
> 
> >>
> 
> >> ...
> 
> >>
> 
> >> py> @simple_decorator
> 
> >>
> 
> >> ... def my_function(a, b, c):
> 
> >>
> 
> >> ...     """Doc string"""
> 
> >>
> 
> >> ...     return a+b+c
> 
> >>
> 
> >> ...
> 
> >>
> 
> >> py> my_function(1, 2, 3)
> 
> >>
> 
> >> Entering decorated function
> 
> >>
> 
> >> Exiting decorated function
> 
> >>
> 
> >> 6
> 
> >>
> 
> >>
> 
> >>
> 
> >> So to me, this is far more magical than nested functions. If I saw this
> 
> >>
> 
> >> in t requires me to hunt through your library for the "simple function
> 
> >>
> 
> >> buried in a utility module somewhere" (your words), instead of seeing
> 
> >>
> 
> >> everything needed in a single decorator factory function. It requires
> 
> >>
> 
> >> that I understand how partial works, which in my opinion is quite tricky.
> 
> >>
> 
> >> (I never remember how it works or which arguments get curried.)
> 
> >>
> 
> >>
> 
> >>
> 
> >> And the end result is that the decorated function is less debugging-
> 
> >>
> 
> >> friendly than I demand: it is an anonymous partial object instead of a
> 
> >>
> 
> >> named function, and the doc string is lost. And it is far from clear to
> 
> >>
> 
> >> me how to modify your recipe to use functools.wraps in order to keep the
> 
> >>
> 
> >> name and docstring, or even whether I *can* use functools.wraps.
> 
> >>
> 
> >>
> 
> >>
> 
> >> I dare say I could answer all those questions with some experimentation
> 
> >>
> 
> >> and research. But I don't think that your "metadecorator" using partial
> 
> >>
> 
> >> is *inherently* more understandable than the standard decorator approach:
> 
> >>
> 
> >>
> 
> >>
> 
> >> def simple_decorator2(func):
> 
> >>
> 
> >>     @functools.wraps(func)
> 
> >>
> 
> >>     def inner(*args, **kwargs):
> 
> >>
> 
> >>         print "Entering decorated function"
> 
> >>
> 
> >>         result = func(*args, **kwargs)
> 
> >>
> 
> >>         print "Exiting decorated function"
> 
> >>
> 
> >>         return result
> 
> >>
> 
> >>     return inner
> 
> >>
> 
> >>
> 
> >>
> 
> >> This is no more complex than yours, and it keeps the function name and
> 
> >>
> 
> >> docstring.
> 
> >>
> 
> >>
> 
> >>
> 
> >>
> 
> >>
> 
> >> > Parameterized decorators are not much more
> 
> >>
> 
> >> > difficult this way.  This function:
> 
> >>
> 
> >> [snip code]
> 
> >>
> 
> >> > And now we have a fancy parameterized decorator that again requires no
> 
> >>
> 
> >> > thinking about nested functions at all.
> 
> >>
> 
> >>
> 
> >>
> 
> >> Again, at the cost of throwing away the function name and docstring.
> 
> >>
> 
> >>
> 
> >>
> 
> >> I realise that a lot of this boils down to personal preference, but I
> 
> >>
> 
> >> just don't think that nested functions are necessarily that hard to
> 
> >>
> 
> >> grasp, so I prefer to see as much of the decorator logic to be in one
> 
> >>
> 
> >> place (a nested decorator function) rather than scattered across two
> 
> >>
> 
> >> separate decorators plus partial.
> 
> 
> 
> Like chi fu, allow decorators to evolve upon themselves. Like simple
> 
> moves flow through water and allow memorization of activity through
> 
> evidence of existence.
> 
> 
> 
> 
> 
> -- 
> 
> Best Regards,


The concept of decorators is just a mapping from a function to another
function with the same name in python.


It should be easy to be grapsed for those studied real analysis and 
functional analysis.
  

[toc] | [prev] | [next] | [standalone]


#29424 — Re: Decorators not worth the effort

FromThomas Rachel <nutznetz-0c1b6768-bfa9-48d5-a470-7603bd3aa915@spamschutz.glglgl.de>
Date2012-09-18 14:16 +0200
SubjectRe: Decorators not worth the effort
Message-ID<k39omn$qe9$1@r03.glglgl.gl>
In reply to#29229
Am 15.09.2012 16:18 schrieb 88888 Dihedral:

> The concept of decorators is just a mapping from a function

... or class ...

 > to another function

... or any other object ...

 > with the same name in python.


Thomas

[toc] | [prev] | [next] | [standalone]


Page 1 of 2  [1] 2  Next page →

Back to top | Article view | comp.lang.python


csiph-web