generator testing and attrs

Discussion in 'Python' started by Mike, Oct 9, 2003.

  1. Mike

    Mike Guest

    I need to be able to store a list of schedulable items, either regular
    callables or generator-producing functions -- is there a way to test if a fn
    is generator-producing? (In the non-generator case, the fn is a 'tick' fn
    that I will call to produce results - a pre-generator implementation.)
    I can test for a generator itself with isinstance(f, types.GeneratorType),
    but I'm interested in the fn that produces it. For example:

    if isGeneratorFn(f):
    f = f()
    f.next() ...
    else:
    f()...

    If not, I guess it's fairly easy to specify a fn attr like so:
    def myGen(): yield foo
    myGen.isGenerator = True

    but this is not as easy for instance methods, it seems. (No?)
    (BTW, +1 from me for PEPs with syntax that let you specify attrs for fn's
    and methods in-line with the def'n for cases like this, 'staticmethod', &c.
    No reason that c# should win on this one...)

    I would call f() the first time and see if the result is a generator object,
    but unfortunately in my case returning a generator is possible valid 'data'
    (to be scheduled later) and doesn't mean I should call .next() straight
    away.

    Ideas?
    thanks
    Mike, Oct 9, 2003
    #1
    1. Advertising

  2. Mike

    Terry Reedy Guest

    "Mike" <> wrote in message
    news:gGfhb.528065$Oz4.405020@rwcrnsc54...
    > I need to be able to store a list of schedulable items, either

    regular
    > callables or generator-producing functions -- is there a way to test

    if a fn
    > is generator-producing?


    Yes, but I forget how. The ref-man section on type hierarchy lists
    and explains 'special attributes' for each type. Functions or code
    objects have an indication of normal vs. generator.

    TJR
    Terry Reedy, Oct 9, 2003
    #2
    1. Advertising

  3. Mike

    Miki Tebeka Guest

    Hello Mike,

    > I need to be able to store a list of schedulable items, either regular
    > callables or generator-producing functions -- is there a way to test if a fn
    > is generator-producing?

    if you do
    >>> def f(): return 1
    >>> dir(f)

    and
    >>> def f(): yield 1

    dir(g)
    You'll see that g has many attributes that f doesnt. Maybe you can use one of them.

    > if isGeneratorFn(f):
    > f = f()
    > f.next() ...
    > else:
    > f()...
    >

    IMO a better way is letting the caller passing you ONLY functions.
    In case of a generator if should pass the .next of the generator.
    e.g.
    l = []
    def add_func(f):
    l.append(f)

    def add_gen(g):
    l.append(g().next)

    for f in l:
    print f()

    HTH.
    Miki
    Miki Tebeka, Oct 10, 2003
    #3
  4. Mike

    Mike Guest

    "Miki Tebeka" <> wrote in message
    > You'll see that g has many attributes that f doesnt. Maybe you can use one

    of them.

    Hmm - doesn't seem so here:

    >>> def g(): yield None
    >>> dir(g)

    ['__call__', '__class__', '__delattr__', '__dict__', '__doc__', '__get__',
    '__getattribute__', '__hash__', '__init__', '__module__', '__name__',
    '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__',
    '__str__', 'func_closure', 'func_code', 'func_defaults', 'func_dict',
    'func_doc', 'func_globals', 'func_name']
    >>> def f(): return None
    >>> dir(f)

    ['__call__', '__class__', '__delattr__', '__dict__', '__doc__', '__get__',
    '__getattribute__', '__hash__', '__init__', '__module__', '__name__',
    '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__',
    '__str__', 'func_closure', 'func_code', 'func_defaults', 'func_dict',
    'func_doc', 'func_globals', 'func_name']
    >>>


    > IMO a better way is letting the caller passing you ONLY functions.
    > In case of a generator if should pass the .next of the generator.
    > ...code...


    As I said, I can't do that becuase I'm saving the items to be scheduled
    (evaluated lazily) -- I don't want to call f() or f.next() right right away.
    (The code sample could have included the comment "# much later..." between
    getting the funarg and calling it.)

    Ahh -- Looks like the original PEP (255) held the key:

    >>> hex(f.func_code.co_flags)

    '0x43'
    >>> hex(g.func_code.co_flags)

    '0x63'
    >>>


    ---
    mike
    Mike, Oct 10, 2003
    #4
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Martin Maurer
    Replies:
    3
    Views:
    4,777
    Peter
    Apr 19, 2006
  2. TheDustbustr
    Replies:
    1
    Views:
    431
    Sami Hangaslammi
    Jul 25, 2003
  3. Replies:
    9
    Views:
    526
  4. Chris Withers

    Problems with email.Generator.Generator

    Chris Withers, Sep 11, 2006, in forum: Python
    Replies:
    20
    Views:
    1,668
    Max M
    Sep 12, 2006
  5. Glen Holcomb
    Replies:
    6
    Views:
    125
    Glen Holcomb
    Oct 29, 2009
Loading...

Share This Page