K
Kjetil Torgrim Homme
often when re-factoring code, I need to change the indent level of
some chunk of code. due to the lack of an end marker, my Emacs has to
use heuristics when re-indenting, and this will occasionally lead to
mistakes. of course this is really _my_ fault, not Emacs', but it's
annoying all the same.
a colleague uses #fi, #yrt etc. to mark the end of blocks, but I don't
find this satisfactory since neither Python nor Emacs has any
knowledge of what the magic comment means.
my suggestion is to allow braces to mark the suites. Python is still
strictly enforcing indentation, in fact, in some ways it's stricter
then before. code which uses braces and is wrongly re-indented will
always cause a syntax error during compilation.
code could look like this:
def appraise_insurance(rental_cars):
{
assert isinstance(rental_cars, (list, tuple))
for car in rental_cars:
{
if car.make == "Lamborghini":
{
car.insurance = 1000.00
}
elif car.make == "Lada":
{
car.insurance = 50.00
}
else:
{
car.insurance = 100.00
}
}
logger.debug("Insurance values updated")
}
now, I don't suggest to write code like that, that has far too much
air between actual codelines. I'd only add the braces where there is
a risk re-indentation changing the meaning of the program, like this:
def appraise_insurance(rental_cars):
assert isinstance(rental_cars, (list, tuple))
for car in rental_cars:
{
if car.make == "Lamborghini":
car.insurance = 1000.00
elif car.make == "Lada":
car.insurance = 50.00
else:
car.insurance = 100.00
}
logger.debug("Insurance values updated")
the single pair of braces is enough. there is now no risk of Emacs
including the debug line into the else branch unnoticed.
the patch to implement this is very simple and restricted to the
tokenizer. as it stands, it requires the braces to be placed as in
the above examples, you _can't_ write
if True: {
code
} else {
code
}
a single braces style improves readability and style consistency among
software projects. my patch does allow two styles, though: to reduce
line count you can put the else: on the same line as the closing
brace.
if True:
{
code
} else:
{
code
}
in both styles, the braces line up and IMHO this makes it easier to
identify where a medium sized block begins and ends.
there can be no code after an opening brace, but it's a good place to
put a comment, so in practice the number of added lines may not be so
large.
a small caveat: it breaks code which looks like this:
def test_varargs1(self):
"""some text"""
{}.has_key(0)
this function is taken from Lib/test/test_call.py, but the doc string
was added to make my patched Python reject it with a syntax error.
the problem is that a brace at the same indent level as the line above
will always mark the beginning of a new suite. I don't think such
code is widespread, but would be interested in hearing contrary
experiences. one fix for this issue is to have the parser tell the
tokenizer whether "a suite may follow" when it asks for the next
token, but I haven't persued writing such a patch.
a patch relative to Python 2.4a2 is available at
http://heim.ifi.uio.no/~kjetilho/hacks/braces-python-2.4a2.patch
what do you think? should I write a PEP?
some chunk of code. due to the lack of an end marker, my Emacs has to
use heuristics when re-indenting, and this will occasionally lead to
mistakes. of course this is really _my_ fault, not Emacs', but it's
annoying all the same.
a colleague uses #fi, #yrt etc. to mark the end of blocks, but I don't
find this satisfactory since neither Python nor Emacs has any
knowledge of what the magic comment means.
my suggestion is to allow braces to mark the suites. Python is still
strictly enforcing indentation, in fact, in some ways it's stricter
then before. code which uses braces and is wrongly re-indented will
always cause a syntax error during compilation.
code could look like this:
def appraise_insurance(rental_cars):
{
assert isinstance(rental_cars, (list, tuple))
for car in rental_cars:
{
if car.make == "Lamborghini":
{
car.insurance = 1000.00
}
elif car.make == "Lada":
{
car.insurance = 50.00
}
else:
{
car.insurance = 100.00
}
}
logger.debug("Insurance values updated")
}
now, I don't suggest to write code like that, that has far too much
air between actual codelines. I'd only add the braces where there is
a risk re-indentation changing the meaning of the program, like this:
def appraise_insurance(rental_cars):
assert isinstance(rental_cars, (list, tuple))
for car in rental_cars:
{
if car.make == "Lamborghini":
car.insurance = 1000.00
elif car.make == "Lada":
car.insurance = 50.00
else:
car.insurance = 100.00
}
logger.debug("Insurance values updated")
the single pair of braces is enough. there is now no risk of Emacs
including the debug line into the else branch unnoticed.
the patch to implement this is very simple and restricted to the
tokenizer. as it stands, it requires the braces to be placed as in
the above examples, you _can't_ write
if True: {
code
} else {
code
}
a single braces style improves readability and style consistency among
software projects. my patch does allow two styles, though: to reduce
line count you can put the else: on the same line as the closing
brace.
if True:
{
code
} else:
{
code
}
in both styles, the braces line up and IMHO this makes it easier to
identify where a medium sized block begins and ends.
there can be no code after an opening brace, but it's a good place to
put a comment, so in practice the number of added lines may not be so
large.
a small caveat: it breaks code which looks like this:
def test_varargs1(self):
"""some text"""
{}.has_key(0)
this function is taken from Lib/test/test_call.py, but the doc string
was added to make my patched Python reject it with a syntax error.
the problem is that a brace at the same indent level as the line above
will always mark the beginning of a new suite. I don't think such
code is widespread, but would be interested in hearing contrary
experiences. one fix for this issue is to have the parser tell the
tokenizer whether "a suite may follow" when it asks for the next
token, but I haven't persued writing such a patch.
a patch relative to Python 2.4a2 is available at
http://heim.ifi.uio.no/~kjetilho/hacks/braces-python-2.4a2.patch
what do you think? should I write a PEP?