Re: Loop with else clause

2019-02-09 Thread DL Neil

Possibly the final contribution:-


On 9/02/19 1:30 AM, Adriaan Renting wrote:


Wow, you dug deep.


=Thank you. It started to 'bug' me, so I really was 'scratching an itch'!



My example was the reverse of the "toy example"'s you mention as I find
that often code becomes much clearer if you order it such that
specific cases, sanity checking and exceptions go first, and then the
default case at the end.


=we have also had this discussion during code reviews. Do you think that 
choice/code sequence/prioritisation is related to one's facility with TDD?

(some might claim it is to do with experience and/or professionalism)

=My observation is that the TDD-people tend to do it 'your way', but 
those who 'first get it working' and then 'go looking for potential 
trouble' do the action-first, and exceptions-later.


=presumption: that the TDD people have thought more about definitions of 
'working' and 'failing' and like to implement all the 'fails' (get them 
'out of the way') in order to leave the 'pure' solution.

(no, let's not disappear too deeply down another 'rabbit hole'!)



So my general suggestion would be to handle your empty list/no valid
candidates cases first,
and then do the for loop at the end.

If you style this with if/elif/else, or put return statements in
certain places, I have no opinion about and will depend on the specific
problem.


...

=I offered the three ideas to the original coder of the actual application:-



Today, kicking ideas around, I coded three other possible 'solutions'



for the review team's discussions:

One of these involves coding three functions: the decision (yielding

a

boolean), the expected-case, and the unusual-case. The satisfaction

in

this was readability factors with a simple if statement..

Somewhat more complex, and I feel a bit OTT, was to sub-class list()

and

write a method which would indicate an empty list, plus include much

of

both the expected-case and the empty-list methods therein. Somehow
"class ListShouldNotBeEmpty" doesn't seem a catchy (if descriptive)
title - however, it works! The decision 'function' could also/then be



made @property and (perhaps) thus contribute to readability.

Lastly, I 'remembered' conditional expressions. Thus, furthering the



idea of two/three functions:

  process_list() if list_has_contents() \
else process_empty_list()



=she has grabbed the class construct and started to 'run with it'. At 
first I feared that I had 'created a monster'. However, once she'd 
improved my outline all manner of other code was filling-in the class. 
It turns-out that the zero-data consideration was not the only way in 
which this data/list varies from the standard. So, she is now monitoring 
how many entries are expected on the list, cf how many have been 
captured, and is planning to evaluate them with a sort & key=.


=Thus my solution, to sub-class from list and (only) modify 
__getitem__(), ie the "lazy" approach, has been changed to monitor the 
creation of the list. She no longer uses anything obvious such as len() 
but is keeping track with several booleans:

1 that there is actually some data,
2 how many elements are in the list,
3 how many elements are required for the application.
(perhaps someone who favored semaphores is going to say "ahah!"?)

=Using the 'toy' example of the film Oscar awards:
1. is exactly as discussed 'here'
2. the traditional use of len()
3. only the top four nominees are mentioned (thus the sort, enables a 
'cursor' featuring only the first four elements), before moving into the 
grand "and the winner is..." (the film receiving the most votes ie 
element[ 0 ] )


=Am almost looking forward to the follow-up code review...


Many thanks (to all) for contributing ideas and advice!
--
Regards =dn
--
https://mail.python.org/mailman/listinfo/python-list


Re: Loop with else clause

2019-02-08 Thread Adriaan Renting


Wow, you dug deep.

My example was the reverse of the "toy example"'s you mention as I find
that often code becomes much clearer if you order it such that
specific cases, sanity checking and exceptions go first, and then the
default case at the end.

So my general suggestion would be to handle your empty list/no valid
candidates cases first,
and then do the for loop at the end.

If you style this with if/elif/else, or put return statements in
certain places, I have no opinion about and will depend on the specific
problem.

Cheers,

Adriaan Renting.

>>> On 7-2-2019 at 9:42, DL Neil 
wrote: 
> Further to our discussion of how to improve a code review's discovery
of 
> the mistaken handling of a for...else... construct:-
> 
> 
> Yesterday was a national holiday, but today gave some opportunity to

> research. Way back in 2009 there was spirited discussion over on the

> Python Ideas list (warning, even the mailing list's index covers 
> multiple screen-lengths):
> 
> - this confusion is not new by any measure, herewith a list of
previous 
> occasions "fists were raised concerning for..else."
>
https://mail.python.org/pipermail/python-ideas/2009-October/006164.html
> 
> - an excellent summary of the 2009 debate which offers no less than
six 
> ways to 'improve' for... else...
>
https://mail.python.org/pipermail/python-ideas/2009-October/006155.html
> 
> - (as mentioned earlier) the BDFL weighed-in a couple of times. His 
> regret is: "That's a flaw, and I don't quite know what to do about
it. 
> It's about 20 years too late to remove or rename it. But we probably

> should not do more of these. That's a lesson."
> (OK, so make that thirty years - older than the coder who the 
> code-review noticed falling into this coding 'gotcha'!)
>
https://mail.python.org/pipermail/python-ideas/2009-October/006083.html
> 
> - herewith a (rather complicated) suggestion, and critique
>
https://mail.python.org/pipermail/python-ideas/2009-October/006054.html
> 
> - one rather hopeful option (actual words to be used
notwithstanding)
>   for i in SEQ:
> A
>   except:
> B
>   else:
> C
> appears here:
>
https://mail.python.org/pipermail/python-ideas/2009-October/006044.html
> 
> 
> Somewhat related, PEP 548 proposed an "More Flexible Loop Control".
This 
> was addressing the confusion caused by break within a loop. It was
rejected.
> 
> 
> Each of the above addresses issues 'within', that is to say
happenings 
> during iteration - whether the entire loop or iteration cut-short by
a 
> break (and thus the idea that "else" might be re-worded to indicate 
> 'after a break').
> 
> However, as mentioned by one contributor, the specific use-case our
team 
> faced was an issue that arises prior to the loop.
Alternately-expressed: 
> that according to Python's logic, prevents even a single iteration of

> that loop. Thus, any 'solution' would reside outside of for and while

> statements because they only consider if a loop should continue or 
> terminate - not handling the question of whether it should start at
all!
> 
> PEP 315 is the only discussion (I've found) which looks 'outside' or

> 'before' the loop itself. It proposed an "Enhanced While Loop", 
> attempting to separate 'setup' or loop control from loop content. It
was 
> rejected.
> 
> 
> So, reading-around brought nothing much useful. Back to the
code-face...
> 
> Thank you to the several folk who responded with ideas to
express/improve:
> 
>  if list:
>  process_list() #the heading and for-loop, as above
>  else:
>  print( "Sorry...
> 
> NB this is a constructed 'toy example' attempting to be the shortest

> illustration of use-cases and invented purely to communicate the need

> and structure. It was expected to be interpreted as
pseudo-python-code. 
> (you'd not use/allow "process_list" as the name of a function, would
you?)
> 
> (With apologies as necessary) one of the dangers of 'toy examples' is

> the reader taking them at face value, instead of as (over-)simplified

> illustrations. In 'real life' the loop code and the no-loop exception

> are both considerably longer than a single line. Accordingly, using a

> function would be a good way to summarise and self-document the 
> activity, ie the if statement's two code-blocks would make the whole

> statement very/too-long (readability)!
> 
> The "if list:" expression is overly-simplistic. The recommendation of

> "if len(list):" is absolutely sound, for reasons of polymorphism.
> 
> In-lieu of a Python construct, there are definitely situations when
use 
> of a sentinel makes better sense. However, given their risk, in many

> ways Python tries to avoid using such, eg consuming iterators until a

> StopIteration exception is returned. (includes files, is subsumed by

> ContextManagers...), thus "pythonic". That said, the classic use of 
> for... else... is in searching for a particular element within an 
> iterable which has all the hallmarks of a "sentinel

Re: Loop with else clause

2019-02-07 Thread DL Neil
Further to our discussion of how to improve a code review's discovery of 
the mistaken handling of a for...else... construct:-



Yesterday was a national holiday, but today gave some opportunity to 
research. Way back in 2009 there was spirited discussion over on the 
Python Ideas list (warning, even the mailing list's index covers 
multiple screen-lengths):


- this confusion is not new by any measure, herewith a list of previous 
occasions "fists were raised concerning for..else."

https://mail.python.org/pipermail/python-ideas/2009-October/006164.html

- an excellent summary of the 2009 debate which offers no less than six 
ways to 'improve' for... else...

https://mail.python.org/pipermail/python-ideas/2009-October/006155.html

- (as mentioned earlier) the BDFL weighed-in a couple of times. His 
regret is: "That's a flaw, and I don't quite know what to do about it. 
It's about 20 years too late to remove or rename it. But we probably 
should not do more of these. That's a lesson."
(OK, so make that thirty years - older than the coder who the 
code-review noticed falling into this coding 'gotcha'!)

https://mail.python.org/pipermail/python-ideas/2009-October/006083.html

- herewith a (rather complicated) suggestion, and critique
https://mail.python.org/pipermail/python-ideas/2009-October/006054.html

- one rather hopeful option (actual words to be used notwithstanding)
for i in SEQ:
  A
except:
  B
else:
  C
appears here:
https://mail.python.org/pipermail/python-ideas/2009-October/006044.html


Somewhat related, PEP 548 proposed an "More Flexible Loop Control". This 
was addressing the confusion caused by break within a loop. It was rejected.



Each of the above addresses issues 'within', that is to say happenings 
during iteration - whether the entire loop or iteration cut-short by a 
break (and thus the idea that "else" might be re-worded to indicate 
'after a break').


However, as mentioned by one contributor, the specific use-case our team 
faced was an issue that arises prior to the loop. Alternately-expressed: 
that according to Python's logic, prevents even a single iteration of 
that loop. Thus, any 'solution' would reside outside of for and while 
statements because they only consider if a loop should continue or 
terminate - not handling the question of whether it should start at all!


PEP 315 is the only discussion (I've found) which looks 'outside' or 
'before' the loop itself. It proposed an "Enhanced While Loop", 
attempting to separate 'setup' or loop control from loop content. It was 
rejected.



So, reading-around brought nothing much useful. Back to the code-face...

Thank you to the several folk who responded with ideas to express/improve:

if list:
process_list() #the heading and for-loop, as above
else:
print( "Sorry...

NB this is a constructed 'toy example' attempting to be the shortest 
illustration of use-cases and invented purely to communicate the need 
and structure. It was expected to be interpreted as pseudo-python-code. 
(you'd not use/allow "process_list" as the name of a function, would you?)


(With apologies as necessary) one of the dangers of 'toy examples' is 
the reader taking them at face value, instead of as (over-)simplified 
illustrations. In 'real life' the loop code and the no-loop exception 
are both considerably longer than a single line. Accordingly, using a 
function would be a good way to summarise and self-document the 
activity, ie the if statement's two code-blocks would make the whole 
statement very/too-long (readability)!


The "if list:" expression is overly-simplistic. The recommendation of 
"if len(list):" is absolutely sound, for reasons of polymorphism.


In-lieu of a Python construct, there are definitely situations when use 
of a sentinel makes better sense. However, given their risk, in many 
ways Python tries to avoid using such, eg consuming iterators until a 
StopIteration exception is returned. (includes files, is subsumed by 
ContextManagers...), thus "pythonic". That said, the classic use of 
for... else... is in searching for a particular element within an 
iterable which has all the hallmarks of a "sentinel".



Today, kicking ideas around, I coded three other possible 'solutions' 
for the review team's discussions:


One of these involves coding three functions: the decision (yielding a 
boolean), the expected-case, and the unusual-case. The satisfaction in 
this was readability factors with a simple if statement..


Somewhat more complex, and I feel a bit OTT, was to sub-class list() and 
write a method which would indicate an empty list, plus include much of 
both the expected-case and the empty-list methods therein. Somehow 
"class ListShouldNotBeEmpty" doesn't seem a catchy (if descriptive) 
title - however, it works! The decision 'function' could also/then be 
made @property and (perhaps) thus contribute to readability.


Lastly, I 'remembered' conditi

Re: Loop with Else Clause

2019-02-05 Thread Christman, Roger Graydon
-Original Message-
From: Python-list  On
Behalf Of DL Neil
Sent: Monday, February 4, 2019 11:29 PM
To: 'Python' 
Subject: Loop with else clause

What is the pythonic way to handle the situation where if a condition exists 
the loop should be executed, but if it does not something else should be done?


--


Just reading this by itself without seeing the illustrative problem, my first 
gut reaction was "while loop!"  but then it became more obvious that this was a 
one-off condition to decide to get started, as opposed to being the loop 
condition itself.


That being said, I would agree that you really cannot do better than the 
if-else already presented, since it is clearly a binary choice:  execute the 
complete loop, or don't if you can't.


I personally try to avoid the else part on both while loops and for loops 
because of this sort of confusion.  All other things being equal, having an 
else section is fundamentally the same thing as simply omitting the 'else:' and 
out-denting the consequence, and makes it very clear just what is going on.


The difference, of course, appears when you have a 'break' within that loop 
that exits prematurely.   And that's where the structured-programming purist in 
me starts to gibber in fear and loathing.  My purist self says that if 'break' 
is applicable, than exception handling is just as applicable with a much 
cleaner model, since you can control where to go next, whether to continue 
repeating, etc.


If I don't expect to get all the way through a for loop, I simply don't write a 
for loop -- I'll substitute with a while, moving the logical negation of the 
break condition into the while loop condition, making it very clear that I 
don't plan to make it to the end.  Unfortunately, the for loop is such a common 
Pythonic thing to do that I really can't say 'for/break' is unPythonic -- I can 
only substitute Lovecraftian adjectives (in my opinion, of course) to describe 
that construct.


But this whole little tangent of mine doesn't seem to apply to your situation 
at all,

and I don't there is a 'single' language element in any programming language I 
can think

of that does what you ask -- so stick with the cleaner: if (__): # loop; else: 
#don't loop


Roger Christman

Pennsylvania State University

-- 
https://mail.python.org/mailman/listinfo/python-list


RE: Loop with else clause

2019-02-05 Thread Avi Gross
The topic is how to deal with a python loop that may not be run if you want
something else to happen in that case. Multiple solutions are presented
along with this request:

> Is there another, more pythonic, approach to conditional (for/while) 
> loop processing?

Has anyone considered looking at this from the perspective of the CONDITION
being evaluated?

If the condition is something simple like is the "list" empty, then any
method will work as it can be evaluated before trying the loop with no side
effects.

But what if the item in question is complex and constructed dynamically as
by zipping things together or calling functions and might even produce side
effects? It might be far from trivial to do that before the loop and check
and you might inadvertently change things. Using a sentinel approach might
be safer.

And what about loops that start but exit immediately without doing anything?
If you iterate on something whose first value is wrong in some way and the
loop starts with an "if ... break" then do you want to do the ELSE condition
because the loop sort of did not run as anticipated? A similar example is if
the loop starts with a "try" and the error handler does a break. 
 


-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Loop with else clause

2019-02-05 Thread Adriaan Renting



I don't know if it is very Pythonic, but I would do something like

if no_oscar_nominees:
print ("Sorry ...")
else:
print_list_of_oscar_nominees()

And yes, that for/else construct can be confusing.

Adriaan.


>>> On 5-2-2019 at 5:29, DL Neil 
wrote: 
> What is the pythonic way to handle the situation where if a condition

> exists the loop should be executed, but if it does not something else

> should be done?
> 
> 
> Why am I asking?
> Today's code review included a for...else structure. I've rarely seen

> such a thing, and even knowing it exists, cannot recall ever using
it! 
> The coder intended to implement the scenario (above) but did not
realise 
> that the else-clause means 'execute if the loop ended without using 
> break'. She thought it meant 'if there's nothing in the iterable, 
> execute the else clause' (per if...then...else... ie the two clauses
are 
> mutually-exclusive*) - which one assumes is the reason why the BDfL
is 
> claimed to have said it should never have been implemented (this
way). 
> She neglected to test the exception properly, and was lulled into a 
> false sense of security by the coverage reporting 100%. Oops!
> 
> *see also the more commonly-used try...except...else...[finally...]
> 
> 
> When/how does this occur?
> Our client is more than a little commercially-sensitive. So as a
really 
> simple scenario, imagine a report is required, naming people who have

> become eligible for something, eg students qualified to enter an 
> advanced class, Oscar film award nominees, entrants who have
fulfilled 
> the requirements of a competition from which a winner will be
randomly 
> selected...
> 
> The names all appear in a list, so the most frequent use-case is
trivial:
> 
>   print( "And the winners are:" )
>   for name in list:
>   print( name )
> 
> but, if no-one actually qualifies, a warning message is required, eg
> 
>   print( "Sorry, no-one is eligible" )
> 
> 
> Possible solution:
> To make anything more than the trivial case readable, I think I'd put

> the list processing into one function, and the exception into another

> (except that this case is so trivial), ie
> 
>   if list:
>   process_list() #the heading and for-loop, as above
>   else:
>   print( "Sorry...
> 
> 
> Others wanted to add a semaphore/flag inside the loop to indicate if
it 
> was executed at least once. Yes, could even use the else clause
then!
> 
> The ideas went (rapidly) down-hill from there...
> 
> 
> Is there another, more pythonic, approach to conditional (for/while)

> loop processing?

-- 
https://mail.python.org/mailman/listinfo/python-list


RE: Loop with else clause

2019-02-05 Thread David Raymond
As mentioned somewhere, "readability counts", so why not just go with exactly 
what you said...

if len(nominees) > 0:#if a condition exists
for nominee in nominees: #the loop should be executed
print(nominee)
else:#but if not
print("D'oh! No one is worthy.") #something else should be done


The fancy features of the language can be cool and all, but forcing yourself to 
use them just for the sake of using them and "being pythonic" can result in 
weird situations, and wrong or unclear assumptions or intents. When someone 
else reads it later it may hide what you were actually intending the check to 
look for.

Hmm, "if nominees:" Did they make it like that to look for a 0 length list, or 
to make sure they didn't get None by accident, or both, or something different?

Hmm, "if len(nominees) > 0:" Ahh ok, we want to make sure there's something in 
there.

So my 2 cents: Feel free to be non-pythonic if it makes things clear and works.


-Original Message-
From: Python-list 
[mailto:python-list-bounces+david.raymond=tomtom@python.org] On Behalf Of 
Peter Otten
Sent: Tuesday, February 05, 2019 3:44 AM
To: python-list@python.org
Subject: Re: Loop with else clause

DL Neil wrote:

> What is the pythonic way to handle the situation where if a condition
> exists the loop should be executed, but if it does not something else
> should be done?

> Possible solution:
> To make anything more than the trivial case readable, I think I'd put
> the list processing into one function, and the exception into another
> (except that this case is so trivial), ie
> 
> if list:
> process_list() #the heading and for-loop, as above
> else:
> print( "Sorry...
> 
> 
> Others wanted to add a semaphore/flag inside the loop to indicate if it
> was executed at least once. Yes, could even use the else clause then!

An argument in favour of the flag is that it works with arbitrary iterables 
whereas if ...: fails:

>>> numbered = enumerate([])
>>> if numbered:
... print("the winners are")
... for ix in numbered: print(*ix)
... 
the winners are
 
> The ideas went (rapidly) down-hill from there...
> 
> 
> Is there another, more pythonic, approach to conditional (for/while)
> loop processing?

I'm not aware of such an approach.

-- 
https://mail.python.org/mailman/listinfo/python-list
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Loop with else clause

2019-02-05 Thread Peter Otten
DL Neil wrote:

> What is the pythonic way to handle the situation where if a condition
> exists the loop should be executed, but if it does not something else
> should be done?

> Possible solution:
> To make anything more than the trivial case readable, I think I'd put
> the list processing into one function, and the exception into another
> (except that this case is so trivial), ie
> 
> if list:
> process_list() #the heading and for-loop, as above
> else:
> print( "Sorry...
> 
> 
> Others wanted to add a semaphore/flag inside the loop to indicate if it
> was executed at least once. Yes, could even use the else clause then!

An argument in favour of the flag is that it works with arbitrary iterables 
whereas if ...: fails:

>>> numbered = enumerate([])
>>> if numbered:
... print("the winners are")
... for ix in numbered: print(*ix)
... 
the winners are
 
> The ideas went (rapidly) down-hill from there...
> 
> 
> Is there another, more pythonic, approach to conditional (for/while)
> loop processing?

I'm not aware of such an approach.

-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Loop with else clause

2019-02-05 Thread Ben Finney
DL Neil  writes:

> Possible solution:
> To make anything more than the trivial case readable, I think I'd put
> the list processing into one function, and the exception into another
> (except that this case is so trivial), ie
>
>   if list:
>   process_list() #the heading and for-loop, as above
>   else:
>   print( "Sorry...

(As an aside: It's best to avoid choosing names like ‘list’ that clobber
built-in names; your code examples are harder to read that way. I'll
assume a different name, ‘ipsums’.)

One aspect of that example I would prefer to avoid: It scatters the
handling of the list to different locations in the code. It's not
obvious from the purpose of ‘process_list’ whether that function should
be handling an empty list; this could lead to double-handling in
different locations.

An alternative to consider::

if ipsums:
for item in ipsums:
process_item(item)
else:
print("Sorry...")

An advantage of this is that the handling of the list is all in the same
place, where changing that logic later will be easier. The
‘process_item’ then just assumes some other code has decided which items
to handle; it becomes correspondingly simpler.

-- 
 \   “Two possibilities exist: Either we are alone in the Universe |
  `\   or we are not. Both are equally terrifying.” —Arthur C. Clarke, |
_o__) 1999 |
Ben Finney

-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Loop with else clause

2019-02-04 Thread DL Neil

On 5/02/19 8:12 PM, Steve wrote:

Would it be a hyphythonitical question?


Is that one of the new meta-classes in release 3.99, or a perhaps a 
project to remove the GIL and take advantage of multi-core architectures?


As well as embarrassing the poor coder, this question vexed quite a few 
minds this afternoon (even allowing for the gathering mood - tomorrow 
being a public holiday!).


Even though it seemed so straightforward to me, others felt it 
reasonable that there would be some way to tell that a loop never 
executed - there must be a simpler, more pythonic, construct...




=
Footnote:
Zamboni locks up after running into large patch of loose teeth.





-Original Message-
From: Python-list  On
Behalf Of DL Neil
Sent: Monday, February 4, 2019 11:29 PM
To: 'Python' 
Subject: Loop with else clause

What is the pythonic way to handle the situation where if a condition exists
the loop should be executed, but if it does not something else should be
done?


Why am I asking?
Today's code review included a for...else structure. I've rarely seen such a
thing, and even knowing it exists, cannot recall ever using it!
The coder intended to implement the scenario (above) but did not realise
that the else-clause means 'execute if the loop ended without using break'.
She thought it meant 'if there's nothing in the iterable, execute the else
clause' (per if...then...else... ie the two clauses are
mutually-exclusive*) - which one assumes is the reason why the BDfL is
claimed to have said it should never have been implemented (this way).
She neglected to test the exception properly, and was lulled into a false
sense of security by the coverage reporting 100%. Oops!

*see also the more commonly-used try...except...else...[finally...]


When/how does this occur?
Our client is more than a little commercially-sensitive. So as a really
simple scenario, imagine a report is required, naming people who have become
eligible for something, eg students qualified to enter an advanced class,
Oscar film award nominees, entrants who have fulfilled the requirements of a
competition from which a winner will be randomly selected...

The names all appear in a list, so the most frequent use-case is trivial:

print( "And the winners are:" )
for name in list:
print( name )

but, if no-one actually qualifies, a warning message is required, eg

print( "Sorry, no-one is eligible" )


Possible solution:
To make anything more than the trivial case readable, I think I'd put the
list processing into one function, and the exception into another (except
that this case is so trivial), ie

if list:
process_list() #the heading and for-loop, as above
else:
print( "Sorry...


Others wanted to add a semaphore/flag inside the loop to indicate if it was
executed at least once. Yes, could even use the else clause then!

The ideas went (rapidly) down-hill from there...


Is there another, more pythonic, approach to conditional (for/while) loop
processing?

--
Regards,
=dn
--
https://mail.python.org/mailman/listinfo/python-list



--
Regards =dn
--
https://mail.python.org/mailman/listinfo/python-list


RE: Loop with else clause

2019-02-04 Thread Steve
Would it be a hyphythonitical question?

= 
Footnote:
Zamboni locks up after running into large patch of loose teeth.

-Original Message-
From: Python-list  On
Behalf Of DL Neil
Sent: Monday, February 4, 2019 11:29 PM
To: 'Python' 
Subject: Loop with else clause

What is the pythonic way to handle the situation where if a condition exists
the loop should be executed, but if it does not something else should be
done?


Why am I asking?
Today's code review included a for...else structure. I've rarely seen such a
thing, and even knowing it exists, cannot recall ever using it! 
The coder intended to implement the scenario (above) but did not realise
that the else-clause means 'execute if the loop ended without using break'.
She thought it meant 'if there's nothing in the iterable, execute the else
clause' (per if...then...else... ie the two clauses are
mutually-exclusive*) - which one assumes is the reason why the BDfL is
claimed to have said it should never have been implemented (this way). 
She neglected to test the exception properly, and was lulled into a false
sense of security by the coverage reporting 100%. Oops!

*see also the more commonly-used try...except...else...[finally...]


When/how does this occur?
Our client is more than a little commercially-sensitive. So as a really
simple scenario, imagine a report is required, naming people who have become
eligible for something, eg students qualified to enter an advanced class,
Oscar film award nominees, entrants who have fulfilled the requirements of a
competition from which a winner will be randomly selected...

The names all appear in a list, so the most frequent use-case is trivial:

print( "And the winners are:" )
for name in list:
print( name )

but, if no-one actually qualifies, a warning message is required, eg

print( "Sorry, no-one is eligible" )


Possible solution:
To make anything more than the trivial case readable, I think I'd put the
list processing into one function, and the exception into another (except
that this case is so trivial), ie

if list:
process_list() #the heading and for-loop, as above
else:
print( "Sorry...


Others wanted to add a semaphore/flag inside the loop to indicate if it was
executed at least once. Yes, could even use the else clause then!

The ideas went (rapidly) down-hill from there...


Is there another, more pythonic, approach to conditional (for/while) loop
processing?

--
Regards,
=dn
--
https://mail.python.org/mailman/listinfo/python-list

-- 
https://mail.python.org/mailman/listinfo/python-list