Re: catching exceptions from an except: block
En Fri, 09 Mar 2007 08:14:18 -0300, Gerard Flanagan <[EMAIL PROTECTED]> escribió: > Mea culpa. Ego te absolvo in nomine Patris Guidii et Filii Python et Spiritus Sancti Computatorium. -- Gabriel Genellina -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
On Mar 9, 11:57 am, "Gabriel Genellina" <[EMAIL PROTECTED]> wrote: > En Fri, 09 Mar 2007 07:30:20 -0300, Gerard Flanagan > <[EMAIL PROTECTED]> escribió: > > >> There is a serious flaw on this approach, the function can't return any > >> false value (it would be treated as a failure). > > > I was teaching myself decorators more than anything, so it's not > > thought out to any extent, but even so I don't think it's a "serious > > flaw", rather it would be programmer error to use @onfailFalse on a > > function that may return False. Don't you think? > > I thought this was on response to the original problem, not for your own > problem. > Mea culpa. Gerard -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
En Fri, 09 Mar 2007 07:30:20 -0300, Gerard Flanagan <[EMAIL PROTECTED]> escribió: >> There is a serious flaw on this approach, the function can't return any >> false value (it would be treated as a failure). > > I was teaching myself decorators more than anything, so it's not > thought out to any extent, but even so I don't think it's a "serious > flaw", rather it would be programmer error to use @onfailFalse on a > function that may return False. Don't you think? I thought this was on response to the original problem, not for your own problem. -- Gabriel Genellina -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
On Mar 9, 9:56 am, "Gabriel Genellina" <[EMAIL PROTECTED]> wrote: > En Fri, 09 Mar 2007 04:49:59 -0300, Gerard Flanagan > <[EMAIL PROTECTED]> escribió: > > > Another version: > > > import exceptions > > As back in time as I could go (Python 1.5), exceptions were available as > builtins... > I did not know that. Thanks. > > def onfailFalse(fn): > > def inner(*args, **kwargs): > > try: > > return fn(*args, **kwargs) > > except ABCException: > > return False > > return inner > > > @onfailFalse > > def a(x): > > if x == 1: > > return 'function a succeeded' > > else: > > raise ABCException() > > There is a serious flaw on this approach, the function can't return any > false value (it would be treated as a failure). > I was teaching myself decorators more than anything, so it's not thought out to any extent, but even so I don't think it's a "serious flaw", rather it would be programmer error to use @onfailFalse on a function that may return False. Don't you think? Gerard -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
En Fri, 09 Mar 2007 05:52:35 -0300, Duncan Booth <[EMAIL PROTECTED]> escribió: > "Gabriel Genellina" <[EMAIL PROTECTED]> wrote: > >> Not the *previous* exception, but the *current* one. You must be >> inside an "except" clause to use a bare raise. >> > No, you don't have to be inside an except clause to use a bare raise. > A bare 'raise' will re-raise the last exception that was active in the > current scope. That applies even outside the except clauses just so long > as there has been an exception within the same function: Oh! Thanks, I didn't know that. I tested it in the interpreter, outside any function, and the exception info was lost immediately, so I wrongly concluded that it lived shortly. -- Gabriel Genellina -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
En Fri, 09 Mar 2007 04:49:59 -0300, Gerard Flanagan <[EMAIL PROTECTED]> escribió: > Another version: > > import exceptions As back in time as I could go (Python 1.5), exceptions were available as builtins... > def onfailFalse(fn): > def inner(*args, **kwargs): > try: > return fn(*args, **kwargs) > except ABCException: > return False > return inner > > @onfailFalse > def a(x): > if x == 1: > return 'function a succeeded' > else: > raise ABCException() There is a serious flaw on this approach, the function can't return any false value (it would be treated as a failure). -- Gabriel Genellina -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
"Gabriel Genellina" <[EMAIL PROTECTED]> wrote: > Not the *previous* exception, but the *current* one. You must be > inside an "except" clause to use a bare raise. > No, you don't have to be inside an except clause to use a bare raise. A bare 'raise' will re-raise the last exception that was active in the current scope. That applies even outside the except clauses just so long as there has been an exception within the same function: e.g. def retry(fn, *args): for attempt in range(3): try: return fn(*args) except: print "retrying attempt", attempt+1 # If we get here we've had too many retries raise >>> import random >>> def testfn(): if random.randint(0,3): raise RuntimeError("oops") return 42 >>> retry(testfn) retrying attempt 1 retrying attempt 2 retrying attempt 3 Traceback (most recent call last): File "", line 1, in retry(testfn) File "", line 4, in retry return fn(*args) File "", line 3, in testfn raise RuntimeError("oops") RuntimeError: oops >>> retry(testfn) retrying attempt 1 retrying attempt 2 42 >>> retry(testfn) 42 -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
On Mar 8, 10:31 am, "Gabriel Genellina" <[EMAIL PROTECTED]> wrote: > En Thu, 08 Mar 2007 06:17:37 -0300, Gerard Flanagan > <[EMAIL PROTECTED]> escribió: > > > @onfail(False) > > def a(x): > > if x == 1: > > return 'function a succeeded' > > else: > > raise > > I know it's irrelevant, as you use a bare except, but such raise looks a > bit ugly... > > -- > Gabriel Genellina Agreed. I thought a 'gentle reader' could have filled in the blanks, but I suppose I should have taken the time to put in a custom exception. Another version: import exceptions class ABCException(exceptions.Exception): pass class DoItException(exceptions.Exception): pass def onfailFalse(fn): def inner(*args, **kwargs): try: return fn(*args, **kwargs) except ABCException: return False return inner @onfailFalse def a(x): if x == 1: return 'function a succeeded' else: raise ABCException() @onfailFalse def b(x): if x == 2: return 'function b succeeded' else: raise ABCException() @onfailFalse def c(x): if x == 3: return 'function c succeeded' else: raise ABCException() def doit(x): for f in [a, b, c]: result = f(x) if result: return result raise DoItException() print doit(1) print doit(2) print doit(3) print doit(4) -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
En Thu, 08 Mar 2007 21:11:54 -0300, Steven D'Aprano <[EMAIL PROTECTED]> escribió: >>> @onfail(False) >>> def a(x): >>> if x == 1: >>> return 'function a succeeded' >>> else: >>> raise > > I thought "raise" on its own was supposed to re-raise the previous > exception, but I've just tried it in the interactive interpreter and it > doesn't work for me. Not the *previous* exception, but the *current* one. You must be inside an "except" clause to use a bare raise. -- Gabriel Genellina -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
Steven D'Aprano <[EMAIL PROTECTED]> writes: > Are you saying it only works as advertised within the except clause of a > try...except block? I think that's the idea. It hadn't occurred to me that it could be used any other way, but I don't have the docs in front of me right now, so maybe I missed something. -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
On Thu, 08 Mar 2007 16:19:27 -0800, Paul Rubin wrote: > Steven D'Aprano <[EMAIL PROTECTED]> writes: >> I thought "raise" on its own was supposed to re-raise the previous >> exception, but I've just tried it in the interactive interpreter and it >> doesn't work for me. > > It means you can catch an exception, do stuff with it, and then pass > it upward to earlier callers: [snip code] Are you saying it only works as advertised within the except clause of a try...except block? -- Steven D'Aprano -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
Steven D'Aprano <[EMAIL PROTECTED]> writes: > I thought "raise" on its own was supposed to re-raise the previous > exception, but I've just tried it in the interactive interpreter and it > doesn't work for me. It means you can catch an exception, do stuff with it, and then pass it upward to earlier callers: def foo(n): try: bar(n) except (ValueError, TypeError): print "invalid n:", n raise # re-signal the same error to foo's caler -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
On Thu, 08 Mar 2007 06:31:20 -0300, Gabriel Genellina wrote: > En Thu, 08 Mar 2007 06:17:37 -0300, Gerard Flanagan > <[EMAIL PROTECTED]> escribió: > >> @onfail(False) >> def a(x): >> if x == 1: >> return 'function a succeeded' >> else: >> raise > > I know it's irrelevant, as you use a bare except, but such raise looks a > bit ugly... I thought "raise" on its own was supposed to re-raise the previous exception, but I've just tried it in the interactive interpreter and it doesn't work for me. >>> raise ValueError # prime a "previous exception" Traceback (most recent call last): File "", line 1, in ? ValueError >>> raise # re-raise the previous exception? Traceback (most recent call last): File "", line 1, in ? TypeError: exceptions must be classes, instances, or strings (deprecated), not NoneType Have I misunderstood? -- Steven D'Aprano -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
En Thu, 08 Mar 2007 06:17:37 -0300, Gerard Flanagan <[EMAIL PROTECTED]> escribió: > @onfail(False) > def a(x): > if x == 1: > return 'function a succeeded' > else: > raise I know it's irrelevant, as you use a bare except, but such raise looks a bit ugly... -- Gabriel Genellina -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
On Mar 7, 7:32 pm, "Arnaud Delobelle" <[EMAIL PROTECTED]> wrote: > Hi all, > > Imagine I have three functions a(x), b(x), c(x) that each return > something or raise an exception. Imagine I want to define a function > that returns a(x) if possible, otherwise b(x), otherwise c(x), > otherwise raise CantDoIt. > (This is my first decorator.) You could also just raise your custom exception rather than having a "retval". Other variations I'm sure are possible. HTH. import exceptions class ABCException(exceptions.Exception): pass def onfail(retval): def outer(fn): def inner(*args, **kwargs): try: return fn(*args, **kwargs) except: return retval return inner return outer @onfail(False) def a(x): if x == 1: return 'function a succeeded' else: raise @onfail(False) def b(x): if x == 2: return 'function b succeeded' else: raise @onfail(False) def c(x): if x == 3: return 'function c succeeded' else: raise def doit(x): for f in [a, b, c]: result = f(x) if result: return result raise ABCException() print doit(1) print doit(2) print doit(3) print doit(4) --- function a succeeded function b succeeded function c succeeded Traceback (most recent call last): File "\working\scratch.py", line 48, in ? print doit(4) File "\working\scratch.py", line 43, in doit raise ABCException() __main__.ABCException shell returned 1 -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
MonkeeSage a écrit : > On Mar 7, 4:58 pm, Bruno Desthuilliers > <[EMAIL PROTECTED]> wrote: >>except_retry: # the missing(???) keyword you're after > > What is 'except_retry'? A totally imaginary statement that would do what the OP is looking for. > To the OP, with the loop and the callables you could also break out of > the loop when the condition is met and use the else condition to raise > the exception. > > def test(arg): > for f in int, float, str, hex: > try: > return f(arg) > break # breaks on f==str You don't need to break here since you're returning. > except: > pass > else: > raise ValueError # remove str above to see this -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
On Wed, 07 Mar 2007 10:32:53 -0800, Arnaud Delobelle wrote: > Hi all, > > Imagine I have three functions a(x), b(x), c(x) that each return > something or raise an exception. Imagine I want to define a function > that returns a(x) if possible, otherwise b(x), otherwise c(x), > otherwise raise CantDoIt. > > Here are three ways I can think of doing it: > > -- > # This one looks ugly > def nested_first(x): > try: > return a(x) > except: > try: > return b(x) > except: > try: > return c(x) > except: > raise CantDoIt Exceptions are great, but sometimes they get in the way. This is one of those times. NULL = object() # get a unique value def result_or_special(func, x): """Returns the result of func(x) or NULL.""" try: return func(x) except Exception: return NULL def failer(x): """Always fail.""" raise CantDoIt def function(x): funcs = (a, b, c, failer) for func in funcs: result = func(x) if result is not NULL: break return result Or if you prefer: def function(x): NULL = object() funcs = (a, b, c) for func in funcs: try: result = func(x) except Exception: pass else: break else: # we didn't break out of the loop raise CantDoIt # we did break out of the loop return result -- Steven D'Aprano -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
On Mar 7, 4:58 pm, Bruno Desthuilliers <[EMAIL PROTECTED]> wrote: >except_retry: # the missing(???) keyword you're after What is 'except_retry'? To the OP, with the loop and the callables you could also break out of the loop when the condition is met and use the else condition to raise the exception. def test(arg): for f in int, float, str, hex: try: return f(arg) break # breaks on f==str except: pass else: raise ValueError # remove str above to see this print test('^&%') Regards, Jordan -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
Arnaud Delobelle schrieb: > On Mar 7, 8:52 pm, Larry Bates <[EMAIL PROTECTED]> wrote: > [snip] >> Without knowing more about the functions and the variable it is somewhat >> hard to tell what you are trying to accomplish. If a, b, c are functions >> that act on x when it is a different type, change to one function that >> can handle all types. > > I'm not really thinking about this situation so let me clarify. Here > is a simple concrete example, taking the following for the functions > a,b,c I mention in my original post. > - a=int > - b=float > - c=complex > - x is a string > This means I want to convert x to an int if possible, otherwise a > float, otherwise a complex, otherwise raise CantDoIt. > > I can do: > > for f in int, float, complex: > try: > return f(x) > except ValueError: > continue > raise CantDoIt > > But if the three things I want to do are not callable objects but > chunks of code this method is awkward because you have to create > functions simply in order to be able to loop over them (this is whay I > was talking about 'abusing loop constructs'). In your case, I don't consider it an abuse - au contraire. Because in such a situation where a possibly growing number of functions dealing with one value until one of them "fits" a loop is the natural thing to do, as it won't change in appearance just because you add a new conversion-function to some (semi-)global list. I'd consider it especially good style in that case. Diez -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
Gabriel Genellina a écrit : > En Wed, 07 Mar 2007 18:48:18 -0300, Arnaud Delobelle > <[EMAIL PROTECTED]> escribió: > >> for f in int, float, complex: >> try: >> return f(x) >> except ValueError: >> continue >> raise CantDoIt >> >> But if the three things I want to do are not callable objects but >> chunks of code this method is awkward because you have to create >> functions simply in order to be able to loop over them (this is whay I >> was talking about 'abusing loop constructs'). Besides I am not happy >> with the other two idioms I can think of. > > > Hmmm, functions are cheap To define. You pay the price when you call them !-) (sorry, couldn't resist - I otherwise totally agree with you) -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
Arnaud Delobelle a écrit : > On Mar 7, 8:52 pm, Larry Bates <[EMAIL PROTECTED]> wrote: > [snip] > >>Without knowing more about the functions and the variable it is somewhat >>hard to tell what you are trying to accomplish. If a, b, c are functions >>that act on x when it is a different type, change to one function that >>can handle all types. > > > I'm not really thinking about this situation so let me clarify. Here > is a simple concrete example, taking the following for the functions > a,b,c I mention in my original post. > - a=int > - b=float > - c=complex > - x is a string > This means I want to convert x to an int if possible, otherwise a > float, otherwise a complex, otherwise raise CantDoIt. > > I can do: > > for f in int, float, complex: > try: > return f(x) > except ValueError: > continue > raise CantDoIt > > But if the three things I want to do are not callable objects but > chunks of code this method is awkward because you have to create > functions You have to write the "chunks of code" anyway, don't you ? So just adding a def statement above each chunk is not such a big deal. Remember that you can define nested funcs, that will close over the namespace of the enclosing one, so you dont necessarily have to pollute the global namespace nor explicitly pass the whole environment to each of these functions. Using the generic higher order func I proposed in a previous answer: def maincode(tati, pouffin): def a(): # some # code # here # that may raise return foo def b(): # some # shorter chunk return bar def c(): # yet # some # other # code return quux return trythese(a, b)() Is it really less readable than: def maincode(tati, pouffin): try: # some # code # here # that may raise return foo except_retry: # the missing(???) keyword you're after # some # shorter chunk return bar except_retry: # yet # some # other # code return quux else: raise CantDoIt > simply in order to be able to loop over them (this is whay I > was talking about 'abusing loop constructs'). Besides I am not happy > with the other two idioms I can think of. > > -- > Arnaud > -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
En Wed, 07 Mar 2007 18:48:18 -0300, Arnaud Delobelle <[EMAIL PROTECTED]> escribió: > for f in int, float, complex: > try: > return f(x) > except ValueError: > continue > raise CantDoIt > > But if the three things I want to do are not callable objects but > chunks of code this method is awkward because you have to create > functions simply in order to be able to loop over them (this is whay I > was talking about 'abusing loop constructs'). Besides I am not happy > with the other two idioms I can think of. Hmmm, functions are cheap - nobody is charging you $2 for each "def" statement you write, I presume :) A bit more serious, if those "chunks of code" are processing its input and returning something that you further process... they *are* functions. If you don't want them to be publicly available, use inner functions: def xxxfactory(x): def f1(x): ... def f2(x): ... def f3(x): ... for f in f1,f2,f3: try: return f(x) ... same as above... -- Gabriel Genellina -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
On Mar 7, 3:04 pm, [EMAIL PROTECTED] wrote: > On Mar 7, 2:48 pm, "Arnaud Delobelle" <[EMAIL PROTECTED]> wrote: > > > > > > > I'm not really thinking about this situation so let me clarify. Here > > is a simple concrete example, taking the following for the functions > > a,b,c I mention in my original post. > > - a=int > > - b=float > > - c=complex > > - x is a string > > This means I want to convert x to an int if possible, otherwise a > > float, otherwise a complex, otherwise raise CantDoIt. > > > I can do: > > > for f in int, float, complex: > > try: > > return f(x) > > except ValueError: > > continue > > raise CantDoIt > > > But if the three things I want to do are not callable objects but > > chunks of code this method is awkward because you have to create > > functions simply in order to be able to loop over them (this is whay I > > was talking about 'abusing loop constructs'). Besides I am not happy > > with the other two idioms I can think of. > > > -- > > Arnaud > > Wouldn't it be easier to do: > > if isinstance(x, int): > # do something > elif isinstance(x, float)t: > # do something > elif isinstance(x, complex): > # do something > else: > raise CantDoIt > > or, > > i = [int, float, complex] > for f in i: > if isinstance(x, f): > return x > else: > raise CantDoIt I so missed the point of this. Not my day. Please ignore my post. -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
Gabriel Genellina a écrit : > En Wed, 07 Mar 2007 19:00:59 -0300, Bruno Desthuilliers > <[EMAIL PROTECTED]> escribió: > >> this kind of cose is exactly what OO polymorphic dispatch is supposed to > > > this kind of cose? sorry s/cose/code/ > Ce genre de chose? > En quelques sortes, oui, quoique pas tout à fait !-) -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
On Mar 7, 2:48 pm, "Arnaud Delobelle" <[EMAIL PROTECTED]> wrote: > > I'm not really thinking about this situation so let me clarify. Here > is a simple concrete example, taking the following for the functions > a,b,c I mention in my original post. > - a=int > - b=float > - c=complex > - x is a string > This means I want to convert x to an int if possible, otherwise a > float, otherwise a complex, otherwise raise CantDoIt. > > I can do: > > for f in int, float, complex: > try: > return f(x) > except ValueError: > continue > raise CantDoIt > > But if the three things I want to do are not callable objects but > chunks of code this method is awkward because you have to create > functions simply in order to be able to loop over them (this is whay I > was talking about 'abusing loop constructs'). Besides I am not happy > with the other two idioms I can think of. > > -- > Arnaud Wouldn't it be easier to do: if isinstance(x, int): # do something elif isinstance(x, float)t: # do something elif isinstance(x, complex): # do something else: raise CantDoIt or, i = [int, float, complex] for f in i: if isinstance(x, f): return x else: raise CantDoIt -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
Arnaud Delobelle a écrit : > Hi all, > > Imagine I have three functions a(x), b(x), c(x) that each return > something or raise an exception. Imagine I want to define a function > that returns a(x) if possible, otherwise b(x), otherwise c(x), > otherwise raise CantDoIt. > > Here are three ways I can think of doing it: > > -- > # This one looks ugly Yes. > def nested_first(x): > try: > return a(x) > except: Try avoiding bare except clauses. It's usually way better to specify the type(s) of exception you're expecting to catch, and let other propagate. > try: > return b(x) > except: > try: > return c(x) > except: > raise CantDoIt > > # This one looks long-winded Yes. And not's very generic. > def flat_first(x): > try: > return a(x) > except: > pass > try: > return b(x) > except: > pass > try: > return c(x) > except: > raise CantDoIt > > # This one only works because a,b,c are functions It works with any callable. Anyway, what else would you use here ??? > # Moreover it seems like an abuse of a loop construct to me Why so ? loops are made for looping, adn functions are objects like any other. > def rolled_first(x): > for f in a, b, c: > try: > return f(x) > except: > continue > raise CantDoIt Here's an attempt at making it a bit more generic (it still lacks a way to specify which kind of exceptions should be silently swallowed. def trythese(*functions): def try_(*args, **kw): for func in functions: try: return func(*args, **kw) except: # FIX ME : bare except clause pass else: # really can't do it, sorry raise CantDoIt return try_ result = trythese(a, b, c)(x) > -- > # This one isn't correct but looks the clearest to me > def wished_first(x): > try: > return a(x) > except: > return b(x) > except: > return c(x) > except: > raise CantDoIt Having multiple except clauses is correct - but it has another semantic. > Note: I've chosen functions a, b, c, but really I'm looking for a way > that is suitable for any chunk of code. A function is an object wrapping a chunk of code... I personnaly find the loop-based approach quite clean and pythonic. -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
On Mar 7, 8:52 pm, Larry Bates <[EMAIL PROTECTED]> wrote: [snip] > Without knowing more about the functions and the variable it is somewhat > hard to tell what you are trying to accomplish. If a, b, c are functions > that act on x when it is a different type, change to one function that > can handle all types. I'm not really thinking about this situation so let me clarify. Here is a simple concrete example, taking the following for the functions a,b,c I mention in my original post. - a=int - b=float - c=complex - x is a string This means I want to convert x to an int if possible, otherwise a float, otherwise a complex, otherwise raise CantDoIt. I can do: for f in int, float, complex: try: return f(x) except ValueError: continue raise CantDoIt But if the three things I want to do are not callable objects but chunks of code this method is awkward because you have to create functions simply in order to be able to loop over them (this is whay I was talking about 'abusing loop constructs'). Besides I am not happy with the other two idioms I can think of. -- Arnaud -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
En Wed, 07 Mar 2007 19:00:59 -0300, Bruno Desthuilliers <[EMAIL PROTECTED]> escribió: > this kind of cose is exactly what OO polymorphic dispatch is supposed to this kind of cose? Ce genre de chose? -- Gabriel Genellina -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
Larry Bates a écrit : (snip) > def d(x): > if isinstance(x, basestring): > # > # Code here for string > # > elif isinstance(x, int): > # > # Code here for int > # > elif isinstance(x, float): > # > # Code here for string > # > else: > raise ValueError As a side note : While there are a few corner cases where this is hardly avoidable (and yet I'd rather test on interface, not on concrete type), this kind of cose is exactly what OO polymorphic dispatch is supposed to avoid (no, don't tell me: I know you can't easily add methods to most builtin types). -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
Miki a écrit : > Hello Arnaud, > > >>Imagine I have three functions a(x), b(x), c(x) that each return >>something or raise an exception. Imagine I want to define a function >>that returns a(x) if possible, otherwise b(x), otherwise c(x), >>otherwise raise CantDoIt. > > Exceptions are for error handling, not flow control. def until(iterable,sentinel): for item in iterable: if item == sentinel: raise StopIteration yield item >>> for item in until(range(10), 5): ... print item ... 0 1 2 3 4 >>> Exceptions *are* a form of flow control. -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
Arnaud Delobelle wrote: > Hi all, > > Imagine I have three functions a(x), b(x), c(x) that each return > something or raise an exception. Imagine I want to define a function > that returns a(x) if possible, otherwise b(x), otherwise c(x), > otherwise raise CantDoIt. > > Here are three ways I can think of doing it: > > -- > # This one looks ugly > def nested_first(x): > try: > return a(x) > except: > try: > return b(x) > except: > try: > return c(x) > except: > raise CantDoIt > > # This one looks long-winded > def flat_first(x): > try: > return a(x) > except: > pass > try: > return b(x) > except: > pass > try: > return c(x) > except: > raise CantDoIt > > # This one only works because a,b,c are functions > # Moreover it seems like an abuse of a loop construct to me > def rolled_first(x): > for f in a, b, c: > try: > return f(x) > except: > continue > raise CantDoIt > -- > > I don't feel happy with any of these. Is there a more satisfying way > of doing this in Python? What I would like is something like: > > -- > # This one isn't correct but looks the clearest to me > def wished_first(x): > try: > return a(x) > except: > return b(x) > except: > return c(x) > except: > raise CantDoIt > -- > > I guess what I'm looking for is some sort of > if: > elif: > ... > elif: > else: > > but for try: except: > That's why > try: > except: > except: > ... > except: > > seemed natural to me :) And I'd like to find a nice way to do this in > a syntactically correct way. > > Note: I've chosen functions a, b, c, but really I'm looking for a way > that is suitable for any chunk of code. > Without knowing more about the functions and the variable it is somewhat hard to tell what you are trying to accomplish. If a, b, c are functions that act on x when it is a different type, change to one function that can handle all types. def d(x): if isinstance(x, basestring): # # Code here for string # elif isinstance(x, int): # # Code here for int # elif isinstance(x, float): # # Code here for string # else: raise ValueError If they are different functions based on type do something like this: # # Set up a dictionary with keys for different types and functions # that correspond. # fdict={type(''): a, type(1): b, type(1.0): c} # # Call the appropriate function based on type # fdict[type(x)](x) -Larry -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
In <[EMAIL PROTECTED]>, Miki wrote: > Exceptions are for error handling, not flow control. That's not true, they are *exceptions* not *errors*. They are meant to signal exceptional situations. And at least under the cover it's used in every ``for``-loop because the end condition is signaled by a `StopIteration` exception. Looks like flow control to me. Ciao, Marc 'BlackJack' Rintsch -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
In <[EMAIL PROTECTED]>, Arnaud Delobelle wrote: > # This one only works because a,b,c are functions > # Moreover it seems like an abuse of a loop construct to me > def rolled_first(x): > for f in a, b, c: > try: > return f(x) > except: > continue > raise CantDoIt > -- Why do you think this is an abuse? I think it's a perfectly valid use of a loop. Ciao, Marc 'BlackJack' Rintsch -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
On 7 Mar, 19:26, "Miki" <[EMAIL PROTECTED]> wrote: > Hello Arnaud, Hi Miki [snip] > Exceptions are for error handling, not flow control. Maybe but it's not always that clear cut! As error handling is a form of flow control the two have to meet somewhere. [snip] > As a side note, try to avoid "catch:", always catch explicit > exceptions. I didn't specify what I wanted to catch because it didn't feel it was relevant to the problem. Thanks -- Arnaud -- http://mail.python.org/mailman/listinfo/python-list
Re: catching exceptions from an except: block
Hello Arnaud, > Imagine I have three functions a(x), b(x), c(x) that each return > something or raise an exception. Imagine I want to define a function > that returns a(x) if possible, otherwise b(x), otherwise c(x), > otherwise raise CantDoIt. Exceptions are for error handling, not flow control. > Here are three ways I can think of doing it: > ... > # This one only works because a,b,c are functions > # Moreover it seems like an abuse of a loop construct to me > def rolled_first(x): > for f in a, b, c: > try: > return f(x) > except: > continue > raise CantDoIt My vote is for that one. > I don't feel happy with any of these. Is there a more satisfying way > of doing this in Python? What I would like is something like: > > -- > # This one isn't correct but looks the clearest to me > def wished_first(x): > try: > return a(x) > except: > return b(x) > except: > return c(x) > except: > raise CantDoIt Again, exception are for error handling, not for flow control. As a side note, try to avoid "catch:", always catch explicit exceptions. HTH, Miki <[EMAIL PROTECTED]> http://pythonwise.blogspot.com -- http://mail.python.org/mailman/listinfo/python-list