Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Blocks for scope control

11 views
Skip to first unread message

Arved Sandstrom

unread,
Jan 15, 2012, 10:50:32 AM1/15/12
to
See
http://stackoverflow.com/questions/1563030/anonymous-code-blocks-in-java
for a general discussion.

I'm talking specifically about the block by itself: a pair of braces by
themselves, enclosing some code in a method. On occasion I do run across
situations where a judicious use of such a block inside a method, to
restrict variable visibility, is handy.

I almost never see anyone else using these things this way. A block in a
method always seems to be associated with a control construct or
exception handling. As any number of references point out, you wouldn't
expect to see many usages of local blocks, mainly because 99 times out
of 100 that situation is probably handled best by a new method. But in
my years of looking at Java it occurs to me that I barely see any use of
this at all...even where it wouldn't be a bad idea.

Any thoughts?

AHS
--
...wherever the people are well informed they can be trusted with their
own government...
-- Thomas Jefferson, 1789

Robert Klemme

unread,
Jan 15, 2012, 11:10:53 AM1/15/12
to
On 15.01.2012 16:50, Arved Sandstrom wrote:
> See
> http://stackoverflow.com/questions/1563030/anonymous-code-blocks-in-java
> for a general discussion.
>
> I'm talking specifically about the block by itself: a pair of braces by
> themselves, enclosing some code in a method. On occasion I do run across
> situations where a judicious use of such a block inside a method, to
> restrict variable visibility, is handy.
>
> I almost never see anyone else using these things this way. A block in a
> method always seems to be associated with a control construct or
> exception handling. As any number of references point out, you wouldn't
> expect to see many usages of local blocks, mainly because 99 times out
> of 100 that situation is probably handled best by a new method. But in
> my years of looking at Java it occurs to me that I barely see any use of
> this at all...even where it wouldn't be a bad idea.
>
> Any thoughts?

I can't remember ever having used a block without flow control inside a
method for other purposes than experimenting with scoping rules. And I
am not missing anything. I believe the fact that variables can be
declared in a for loop header as well as that all loops and if-else open
a new scope (as well as methods, of course) is responsible for me never
using blocks inside methods. IMHO chances are that if you need one or
more blocks inside methods that these things are pretty independent and
better handled by a method call which has the added benefit of providing
documentation via the method name, if chosen wisely.

Kind regards

robert

--
remember.guy do |as, often| as.you_can - without end
http://blog.rubybestpractices.com/
Message has been deleted

Robert Klemme

unread,
Jan 15, 2012, 11:32:26 AM1/15/12
to
On 15.01.2012 17:18, Stefan Ram wrote:
> Arved Sandstrom<asandstr...@eastlink.ca> writes:
>> Any thoughts?
>
> Im using this whenever it makes sense. For example,
> say you wanted to add a button:
>
> { final Button button = new Button(); frame.add( button ); }

Why do you think it makes sense to replace this

frame.add( new Button() );

with the block above? If initialization is more complex, I'd rather do this

frame.add( createButton() );

than

> or apply the refactor »extract method«:
>
> void m( final Frame frame )
> { final Button button = new Button(); frame.add( button ); }

Cheers
Message has been deleted

markspace

unread,
Jan 15, 2012, 12:57:50 PM1/15/12
to
On 1/15/2012 7:50 AM, Arved Sandstrom wrote:

> I almost never see anyone else using these things this way.


IMO, I dislike spurious and overused indentation in code, so that's
likely why I shy away from "extra" use of braces.

for( ...some code )
{
do some init
{
do a little work
{
declare a temporary variable
}
{
declare another temporary variable
}
{
declare yet another temporary variable
}
{
declare still yet another temporary variable
{
declare a temporary variable inside
an anonymous block
}
}
}
}

vs. just one level of indentation, I believe I'd greatly prefer the
latter, especially in the long run. And the above is with 3-4 spaces
for indenting, imagine what it would look like with 8.


Lew

unread,
Jan 15, 2012, 2:00:39 PM1/15/12
to
Arved Sandstrom wrote:
> See
> http://stackoverflow.com/questions/1563030/anonymous-code-blocks-in-java
> for a general discussion.
>
> I'm talking specifically about the block by itself: a pair of braces by
> themselves, enclosing some code in a method. On occasion I do run across
> situations where a judicious use of such a block inside a method, to
> restrict variable visibility, is handy.
>
> I almost never see anyone else using these things this way. A block in a
> method always seems to be associated with a control construct or
> exception handling. As any number of references point out, you wouldn't
> expect to see many usages of local blocks, mainly because 99 times out
> of 100 that situation is probably handled best by a new method. But in
> my years of looking at Java it occurs to me that I barely see any use of
> this at all...even where it wouldn't be a bad idea.
>
> Any thoughts?

You see it standardly in initialization blocks, especially static, though I
often (more often than not) find myself refactoring static initialization
blocks to private static methods. For instance initialization they're
extremely useful for blocks that multiple constructors must share.

Within methods I use them as well, to enforce temporariness of variables.
This is very handy to prevent re-use of a variable whose usefulness has
expired. The need is rare, but like the legendary left-handed stembolt, if
you don't have it when you need it, that's a worry.

This idiom is also valid in other languages (e.g., C).

Calling such code blocks "anonymous" doesn't make sense. Code blocks aren't
named in the first place.

There are many, many idioms in Java that are woefully underused. 'assert' is
the prime example. People don't understand it, even excoriate it (strange as
that seems), and it's been around about a decade, since Java 1.4. Lack of use
does not equate to lack of value.

--
Lew
Honi soit qui mal y pense.
http://upload.wikimedia.org/wikipedia/commons/c/cf/Friz.jpg

Lew

unread,
Jan 15, 2012, 2:21:42 PM1/15/12
to
Stefan Ram wrote:
> Robert Klemm writes:
>>> { final Button button = new Button(); frame.add( button ); }
>> Why do you think it makes sense to replace this
>> frame.add( new Button() );
>> with the block above?
>
> This code (comments removed by me):
>
> for (ThumbnailAction thumbAction : chunks) {
> JButton thumbButton = new JButton(thumbAction);
> buttonBar.add(thumbButton, buttonBar.getComponentCount() - 1);
> }
>
> can be found in the renowned Java Tutorial at
>
> http://docs.oracle.com/javase/tutorial/uiswing/components/icon.html
>
> . So such temporary names for one-time use are not
> against common teachings.

Some argue, and there's merit in the position, that the one-time name idiom
enhances code readability over the constructor-in-the-method-argument idiom.

(I also find merit in the "you ought to know Java well enough to read a
friggin' construction in an argument, for God's sake" argument, for anyone
claiming remuneration for their Java skills. Lacking such knowledge and
charging for your Java skills is fraud if the ignorance is not disclosed up
front.)

Lew

unread,
Jan 15, 2012, 2:28:38 PM1/15/12
to
Since eight-space indentation violates the Java coding conventions it doesn't
deserve consideration. Code that indents eight spaces should be rejected in
code review and brought into compliance.

<http://www.oracle.com/technetwork/java/codeconventions-136091.html#262>

But your larger point is valid, and you can just do this:

for( ...some code )
{
do some init
do a little work
declare a temporary variable
declare another temporary variable
declare yet another temporary variable
declare still yet another temporary variable
declare a temporary variable inside
}

The reason to go with the supposedly "extra" braces is to guarantee that a
temporary variable is not re-used, but if a method is so long that that's a
risk there's a good chance that it's too long.

And again I say, "anonymous block" makes no sense because blocks aren't named
in the first place.

Arved Sandstrom

unread,
Jan 15, 2012, 4:49:26 PM1/15/12
to
On 12-01-15 03:00 PM, Lew wrote:
> Arved Sandstrom wrote:
>> See
>> http://stackoverflow.com/questions/1563030/anonymous-code-blocks-in-java
>> for a general discussion.
>>
>> I'm talking specifically about the block by itself: a pair of braces by
>> themselves, enclosing some code in a method. On occasion I do run across
>> situations where a judicious use of such a block inside a method, to
>> restrict variable visibility, is handy.
>>
>> I almost never see anyone else using these things this way. A block in a
>> method always seems to be associated with a control construct or
>> exception handling. As any number of references point out, you wouldn't
>> expect to see many usages of local blocks, mainly because 99 times out
>> of 100 that situation is probably handled best by a new method. But in
>> my years of looking at Java it occurs to me that I barely see any use of
>> this at all...even where it wouldn't be a bad idea.
>>
>> Any thoughts?
>
> You see it standardly in initialization blocks, especially static,
> though I often (more often than not) find myself refactoring static
> initialization blocks to private static methods. For instance
> initialization they're extremely useful for blocks that multiple
> constructors must share.

At the instance and class levels, it's true, these blocks operate
similarly to "local" blocks.

> Within methods I use them as well, to enforce temporariness of
> variables. This is very handy to prevent re-use of a variable whose
> usefulness has expired. The need is rare, but like the legendary
> left-handed stembolt, if you don't have it when you need it, that's a
> worry.

This is exactly the use I was calling out. After visibility modifiers we
then have a number of levels of scope - class, instance, method and
block. We already use restrictive variable scoping in blocks; everyone
who re-uses for-loop index names benefits from this.

My point is simply that on some occasions, as you point out yourself,
you do want to "enforce temporariness" of a variable in a scope narrower
than that of its enclosing method. The answer here, on those infrequent
occasions where it makes sense to use a block, is not to blindly create
a new method simply to get variable scoping. That reflexive practice can
lead to unreadable fragmented code.

> This idiom is also valid in other languages (e.g., C).
>
> Calling such code blocks "anonymous" doesn't make sense. Code blocks
> aren't named in the first place.

Well, to be fair, *I* didn't call them "anonymous", the original poster
at StackOverflow did. :-) Strictly speaking they are blocks, and nothing
but blocks; in order to specify more exactly what type of block I meant
I referred to them as "local blocks".

> There are many, many idioms in Java that are woefully underused.
> 'assert' is the prime example. People don't understand it, even
> excoriate it (strange as that seems), and it's been around about a
> decade, since Java 1.4. Lack of use does not equate to lack of value.
>
Quite apart from (lack of) understanding as to how to apply assertions
effectively and correctly, I believe that there are other reasons why
they are not more widely used. Some are good, some not so good, some are
neutral.

I'm with you on this one, though. I like assertions and use them.

Lew

unread,
Jan 15, 2012, 6:45:31 PM1/15/12
to
Arved Sandstrom wrote:
> Lew wrote:
>> There are many, many idioms in Java that are woefully underused.

Okay, not all that many, but some.

>> 'assert' is the prime example. People don't understand it, even
>> excoriate it (strange as that seems), and it's been around about a
>> decade, since Java 1.4. Lack of use does not equate to lack of value.
>>
> Quite apart from (lack of) understanding as to how to apply assertions
> effectively and correctly, I believe that there are other reasons why
> they are not more widely used. Some are good, some not so good, some are
> neutral.
>
> I'm with you on this one, though. I like assertions and use them.

I am curious as to the "good" reasons why they're not more widely used. I can
think of none I'd categorize as "good".

There are good reasons not to use them in certain scenarios, e.g., they are
not intended nor should be used for checking arguments to public methods, but
that doesn't speak to why 'assert' isn't more widely used for the intended use
cases.

Robert Klemme

unread,
Jan 16, 2012, 1:55:58 AM1/16/12
to
On 15.01.2012 22:49, Arved Sandstrom wrote:
> On 12-01-15 03:00 PM, Lew wrote:
>> Arved Sandstrom wrote:
>> You see it standardly in initialization blocks, especially static,
>> though I often (more often than not) find myself refactoring static
>> initialization blocks to private static methods. For instance
>> initialization they're extremely useful for blocks that multiple
>> constructors must share.
>
> At the instance and class levels, it's true, these blocks operate
> similarly to "local" blocks.

That's also a feature I use from time to time. But I thought this
discussion was more about blocks inside methods since initializer blocks
are a quite different beast (you can view them as anonymous methods
without arguments and return type).

>> Within methods I use them as well, to enforce temporariness of
>> variables. This is very handy to prevent re-use of a variable whose
>> usefulness has expired. The need is rare, but like the legendary
>> left-handed stembolt, if you don't have it when you need it, that's a
>> worry.
>
> This is exactly the use I was calling out. After visibility modifiers we
> then have a number of levels of scope - class, instance, method and
> block. We already use restrictive variable scoping in blocks; everyone
> who re-uses for-loop index names benefits from this.
>
> My point is simply that on some occasions, as you point out yourself,
> you do want to "enforce temporariness" of a variable in a scope narrower
> than that of its enclosing method. The answer here, on those infrequent
> occasions where it makes sense to use a block, is not to blindly create
> a new method simply to get variable scoping. That reflexive practice can
> lead to unreadable fragmented code.

But there are other blocks which also restrict scope (i.e. flow
control). So more often than not I find myself using those. Plus, I
now have made it a habit to make variables final as often as possible
(mostly for documentation reasons) and thusly also prevent accidental reuse.

Regarding the method refactoring argument: if there is so much code and
hence so many local variables that you want to use blocks to introduce
smaller scopes chances are that the logic within that blocks is also
largely independent from the code around so it is a good candidate for
refactoring anyway. The reason for refactoring into methods isn't the
scope but the independent logic.

Kind regards

Robert Klemme

unread,
Jan 16, 2012, 1:59:19 AM1/16/12
to
On 15.01.2012 17:59, Stefan Ram wrote:
> Robert Klemme<short...@googlemail.com> writes:
>>> { final Button button = new Button(); frame.add( button ); }
>> Why do you think it makes sense to replace this
>> frame.add( new Button() );
>> with the block above?
>
> This code (comments removed by me):
>
> for (ThumbnailAction thumbAction : chunks) {
> JButton thumbButton = new JButton(thumbAction);
> buttonBar.add(thumbButton, buttonBar.getComponentCount() - 1);
> }
>
> can be found in the renowned Java Tutorial at
>
> http://docs.oracle.com/javase/tutorial/uiswing/components/icon.html
>
> . So such temporary names for one-time use are not
> against common teachings.

OK, but here there are more arguments to add() and the line is longer.
That makes more sense than the original example to me.

Roedy Green

unread,
Jan 16, 2012, 9:09:36 AM1/16/12
to
On Sun, 15 Jan 2012 11:50:32 -0400, Arved Sandstrom
<asandstr...@eastlink.ca> wrote, quoted or indirectly quoted
someone who said :

>Any thoughts?

I use them fairly often for this construct:
{
FastCat sb = new FastCat( 2);
sb.append( "xxx");
sb.append( "yyyy");
thing = sb.toString();
}

{
FastCat sb = new FastCat( 2);
sb.append( "zzz");
if ( q )
{
sb.append( "aaa");
}
another = sb.toString();
}
--
Roedy Green Canadian Mind Products
http://mindprod.com
One of the most useful comments you can put in a program is
"If you change this, remember to change ?XXX? too".

Henk van Voorthuijsen

unread,
Jan 16, 2012, 10:03:13 AM1/16/12
to
On Jan 16, 3:09 pm, Roedy Green <see_webs...@mindprod.com.invalid>
wrote:
>
> I use them fairly often for this construct:
>   {
>   FastCat sb = new FastCat( 2);
>   sb.append( "xxx");
>   sb.append( "yyyy");
>   thing = sb.toString();
>   }
>
>   {
>   FastCat sb = new FastCat( 2);
>   sb.append( "zzz");
>   if ( q )
>     {
>     sb.append( "aaa");
>     }
>   another = sb.toString();
>   }

Interesting cae, but even here I would be inclined to use a variation
of "extract method":

thing = cat("xxx", "yyyy");

String cat(String... strings) {
FastCat sb = new FastCat( 2);
for (String str: strings) {
sb.append(str);
}
}

...




Arne Vajhøj

unread,
Jan 17, 2012, 6:43:58 PM1/17/12
to
On 1/15/2012 10:50 AM, Arved Sandstrom wrote:
> See
> http://stackoverflow.com/questions/1563030/anonymous-code-blocks-in-java
> for a general discussion.
>
> I'm talking specifically about the block by itself: a pair of braces by
> themselves, enclosing some code in a method. On occasion I do run across
> situations where a judicious use of such a block inside a method, to
> restrict variable visibility, is handy.
>
> I almost never see anyone else using these things this way. A block in a
> method always seems to be associated with a control construct or
> exception handling. As any number of references point out, you wouldn't
> expect to see many usages of local blocks, mainly because 99 times out
> of 100 that situation is probably handled best by a new method. But in
> my years of looking at Java it occurs to me that I barely see any use of
> this at all...even where it wouldn't be a bad idea.
>
> Any thoughts?

I can see couple of reasons why it is not used much:

1) The average Java developer is not aware of the possibility.

2) If a method is so complex that this trick has a significant effect
for avoiding mistakes, then the method should be broken up in
multiple smaller methods.

Arne



Arved Sandstrom

unread,
Jan 19, 2012, 8:16:36 PM1/19/12
to
On 12-01-16 02:55 AM, Robert Klemme wrote:
> On 15.01.2012 22:49, Arved Sandstrom wrote:
[ SNIP ]

>> This is exactly the use I was calling out. After visibility modifiers we
>> then have a number of levels of scope - class, instance, method and
>> block. We already use restrictive variable scoping in blocks; everyone
>> who re-uses for-loop index names benefits from this.
>>
>> My point is simply that on some occasions, as you point out yourself,
>> you do want to "enforce temporariness" of a variable in a scope narrower
>> than that of its enclosing method. The answer here, on those infrequent
>> occasions where it makes sense to use a block, is not to blindly create
>> a new method simply to get variable scoping. That reflexive practice can
>> lead to unreadable fragmented code.
>
> But there are other blocks which also restrict scope (i.e. flow
> control). So more often than not I find myself using those. Plus, I
> now have made it a habit to make variables final as often as possible
> (mostly for documentation reasons) and thusly also prevent accidental
> reuse.

Also a good practice. There is some irony in you mentioning this,
insofar as most programmers don't do this either...usually because they
don't see anyone else doing it. Which leads to a situation where one
needs to justify using "final" as often as possible, rather than the
burden of justification being the other way around.

I know there's the perennial debate about final classes, but final
variables are a different ball of wax. I rather wish folks thought the
way you did, and maybe then a coder would have to justify *not* making a
variable final.

> Regarding the method refactoring argument: if there is so much code and
> hence so many local variables that you want to use blocks to introduce
> smaller scopes chances are that the logic within that blocks is also
> largely independent from the code around so it is a good candidate for
> refactoring anyway. The reason for refactoring into methods isn't the
> scope but the independent logic.
>
> Kind regards
>
> robert
>
To focus on your points above, you _would_ refactor into
methods...*except* for those few cases where the methods end up being
trivial, and because the method body is located elsewhere you lose some
perspective on your code, and the replacement of the potential local
blocks with methods obscures the calling code.

Let me give you an example. Some days prior to writing my post I had to
write some code that processed a number of items in a similar fashion.
Each item was a matter of 2 or 3 lines of code. In theory each process
could have been collapsed into one very long line with multiple
duplicated and chained method calls, rather than use temporary local
variables, but I abhor this practice. So for clarity I kept the
operations on each item as 2 or 3 lines of code with at least one
temporary local variable.

Although the type of the local variable was the same, the operations
that produced it were not - they depended on the item. So any method
that would have replaced all these individually simple simple groups of
operations would have been either a moderately complex switch or a
moderately complex if-else if-else structure, less easy to understand,
and more error-prone. Furthermore, a flag would have been necessary to
the method to indicate which branch to take.

As you may have guessed this logic had to do with post-processing
various String and Boolean command-line options delivered by a
command-line processor. Quite frankly there is nothing pretty about
this, and there never has been in any language I've ever used - all you
can hope for is to keep the code clear, as error-free as possible, as
change-proof as possible (one of the main reasons for me using local
blocks actually), and just tolerate the boilerplate processing otherwise.

So this is one example, and I think a decent one. I don't think I
actually need to defend it, because a block is a legitimate language
construct, and you may wish to use them sometimes rather than end up
with mini-methods.

However, the intent of the thread was to get some feedback, and I thank
you all for it.

Arved Sandstrom

unread,
Jan 19, 2012, 8:54:05 PM1/19/12
to
Lew, I had side-effects of assertions in mind when I wrote that, for
one. I know, and you know, that Java docs on assertions clearly point
out that assertions should not have side-effects, that you should be
able to omit their execution and not affect the remaining code. However,
good intentions and all, a widespread use of assertions by developers
who haven't thoroughly checked the assertion logic to ensure its purity
may lead to testing anomalies.

As an example, what if the condition you wish to assert at a specific
point has no immediately available variables to work with? It might be a
temptation for a programmer to call some getters to obtain the values.
As we know, many getters are not side-effect free, even ones that ought
to be, and unless a coder religiously checks this out there may be a
problem. A novice coder might not notice that a getter is synchronized,
as an example, and simply note the fact that the getter itself does
nothing but return a value.

Perhaps not a "good" reason, but I'd call it a realistic one.

Yes, the Java assertion documentation happens to use an example where a
local variable is conveniently produced by a previous necessary piece of
logic, and the following assertion can happily use that value. Not
always so easy.

Another decent reason, in my opinion, is if the management of them is
not disciplined. An organization that doesn't even wonder whether they
are disciplined enough to manage assertions in code isn't, and others
that do ask the question may decide that they are not.

What I mean by this is, assertions are easy to put in. They are not
always correct when put in, and they have to be maintained in any case
as code changes (or at least removed if necessary). Existing obsolete
assertions need to be taken into account when adding new ones in the
same class or package, because if you enable one then you may enable
more. Or you remove old ones you don't understand, if you trust yourself
to understand the business rules from 4 years ago well enough to
classify the assertions as being defunct.

Let me put it this way: I would feel good about looking at code that had
assertions in it if I saw that they were also commented where necessary,
including traceability notes where that makes sense, *and* were
supported by unit tests that exercised the assertions.

Again, you may wish to not think of this as a "good" reason. It's not
really. It's another realistic reason. I've worked with a number of
development teams that, if they were ever to read about assertions and
get a wild hair about trying them, would either be useless with them or
be obstructive with them. It may not be a "good" thing that they don't
use assertions, but it's not a bad thing either.

Robert Klemme

unread,
Jan 20, 2012, 2:41:01 AM1/20/12
to
On 20.01.2012 02:54, Arved Sandstrom wrote:
> Another decent reason, in my opinion, is if the management of them is
> not disciplined. An organization that doesn't even wonder whether they
> are disciplined enough to manage assertions in code isn't, and others
> that do ask the question may decide that they are not.

I think this does not necessarily need to be handled on organization
level. Why make it so big? Every developer can help himself and their
colleagues by using them in a reasonable way.

> What I mean by this is, assertions are easy to put in. They are not
> always correct when put in, and they have to be maintained in any case
> as code changes (or at least removed if necessary). Existing obsolete
> assertions need to be taken into account when adding new ones in the
> same class or package, because if you enable one then you may enable
> more. Or you remove old ones you don't understand, if you trust yourself
> to understand the business rules from 4 years ago well enough to
> classify the assertions as being defunct.

Assertions also have the effect that they force you to think about
certain - possibly not obvious - properties of the code / class at hand
when you change the code. So while an assertion may look tricky it
actually helps you when modifying code to not forget important aspects.
This may be more tedious but it certainly helps code robustness in the
long run.

> Let me put it this way: I would feel good about looking at code that had
> assertions in it if I saw that they were also commented where necessary,
> including traceability notes where that makes sense, *and* were
> supported by unit tests that exercised the assertions.

I view assertions in part also as documentation. Often no additional
commenting is needed. I frequently have a private boolean method
"classInvariant" or with other (hopefully telling) name with checks and
has documentation of its own. In these cases you have the name of the
method plus documentation on the method.

Kind regards
Message has been deleted
Message has been deleted

Lew

unread,
Jan 20, 2012, 2:05:08 PM1/20/12
to
On 01/20/2012 07:34 AM, Stefan Ram wrote:
> r...@zedat.fu-berlin.de (Stefan Ram) writes:
>> { final Button button = new Button(); frame.add( button ); }
>
> I also use blocks to clarify the scope of a comment
> (when extracting a method is no better solution):
>
> alpha();
> { /* add a button to the frame */
> final Button button = new Button();
> frame.add( button ); }
> beta();
>
> I teach both the use of omitable [sic] »final« keywords and the
> use of omitable blocks (which both serve only to enhance
> readability) in my classes right from the beginnig. In fact,
> I start to teach /all/ variable declaration and parameter
> declarations with »final« and later explain when »final« can
> be removed.
>
> (Many English dictionaries do not have an entry »omitable« [sic].
> This word is intended to mean the following above: An omitable [sic]
> part of the source code often [but not necessarily always]
> can be removed without changing the behavior of the program.)

Dictionaries frequently do not list all possible inflections of a word. In
this case they undoubtedly leave it to the normal rules of English to produce
"omittable" (note the double "t") without a separate entry.
Message has been deleted

Gene Wirchenko

unread,
Jan 20, 2012, 3:11:23 PM1/20/12
to
On 20 Jan 2012 15:34:51 GMT, r...@zedat.fu-berlin.de (Stefan Ram)
wrote:

>r...@zedat.fu-berlin.de (Stefan Ram) writes:
>>{ final Button button = new Button(); frame.add( button ); }
>
> I also use blocks to clarify the scope of a comment
> (when extracting a method is no better solution):
>
>alpha();
>{ /* add a button to the frame */
> final Button button = new Button();
> frame.add( button ); }
>beta();

I dislike block ends at the end of a line.

I use blank lines myself and comment headers with bigger, oh,
call them "wings".

*
*
* This is a high-level comment.
*
*

code
code

*
* This is a less high-level comment.
*

code
code

* This is a fairly tactical comment.

code
code

* This a block comment.
code
code && and this is a line comment.
&& Sometimes continued.
code

I usually do not use wings and rarely use two line wings. If I
add a lesser comment to a winged comment, I put it after the
after-wing, as in:

*
* This is a less high-level comment.
*
* If you modify this code, check over OtherCode() as well.

> I teach both the use of omitable »final« keywords and the
> use of omitable blocks (which both serve only to enhance
> readability) in my classes right from the beginnig. In fact,
> I start to teach /all/ variable declaration and parameter
> declarations with »final« and later explain when »final« can
> be removed.
>
> (Many English dictionaries do not have an entry »omitable«.
> This word is intended to mean the following above: An omitable
> part of the source code often [but not necessarily always]
> can be removed without changing the behavior of the program.)

It was surprising to me that there was apparently no such word of
capable of being omitted. It turns out that it is irregular. The
word you want is "omissible":
http://dictionary.reference.com/browse/omissible

Sincerelyk,

Gene Wirchenko


Message has been deleted

Lew

unread,
Jan 20, 2012, 6:24:52 PM1/20/12
to
On 01/20/2012 12:07 PM, Stefan Ram wrote:
> Robert Klemme<short...@googlemail.com> writes:
>> commenting is needed. I frequently have a private boolean method
>> "classInvariant" or with other (hopefully telling) name with checks and
>
> private static boolean classInvariant(){ ... }
> private boolean objectInvariant(){ ... }
>
> However, since it's boolean, I prefer »is«- or »has«-names:
>
> boolean isValid(){ ... }
>
> . One can compare the readability of:
>
> if( this.classInvariant() )...
>
> and
>
> if( this.isValid() )...
>
> .

There is rarely, if ever, a good reason to qualify a method name with 'this.'
It does not affect the semantics of the statement, and as documentation is
misleading.

The canonical mechanism to prove invariants is the 'assert' statement. It is
a compiler- and runtime-enforced program comment.

Arved Sandstrom

unread,
Jan 20, 2012, 6:30:38 PM1/20/12
to
On 12-01-20 03:41 AM, Robert Klemme wrote:
> On 20.01.2012 02:54, Arved Sandstrom wrote:
>> Another decent reason, in my opinion, is if the management of them is
>> not disciplined. An organization that doesn't even wonder whether they
>> are disciplined enough to manage assertions in code isn't, and others
>> that do ask the question may decide that they are not.
>
> I think this does not necessarily need to be handled on organization
> level. Why make it so big? Every developer can help himself and their
> colleagues by using them in a reasonable way.

When I say "organization" I don't mean company necessarily. I really
mean team or developer group. Although for a very small company it'll
end up being the same thing.

There are obviously differing opinions here, but I don't myself think
that the use of assertions is something you want to leave up to
individual developers. The fact that they are being used, and the
initial decision to use them, ought to be discussed and coordinated and
communicated across the project team.
I also view assertions as documentation. I consider them important
enough in this role that I dislike casual and/or trivial use of
assertions, because pointless assertions can obscure the role of
genuinely important ones. Another reason why I think there ought to be
some team guidelines on these things.

Lew

unread,
Jan 20, 2012, 6:54:11 PM1/20/12
to
Arved Sandstrom wrote:
> Robert Klemme wrote:
>> Arved Sandstrom wrote:
>>> ... [snip] ...
> There are obviously differing opinions here, but I don't myself think
> that the use of assertions is something you want to leave up to
> individual developers. The fact that they are being used, and the
> initial decision to use them, ought to be discussed and coordinated and
> communicated across the project team.

+1 not least because of the endemic ignorance and superstition around
'assert'. A team discussion and documentation can elucidate the sound
engineering principles behind when to use and not use the idiom.

>>> What I mean by this is, assertions are easy to put in. They are not
>>> always correct when put in, and they have to be maintained in any case
>>> as code changes (or at least removed if necessary). Existing obsolete
>>> assertions need to be taken into account when adding new ones in the
>>> same class or package, because if you enable one then you may enable
>>> more. Or you remove old ones you don't understand, if you trust yourself
>>> to understand the business rules from 4 years ago well enough to
>>> classify the assertions as being defunct.

Assertions are about algorithmic invariants. Being invariant, they shouldn't
change, and then only when such fundamental algorithmic changes are underway
that a responsible organization would carefully document them anyway.

The effort to place assertions correctly is closely tied to the effort to
understand the algorithm properly.

>> Assertions also have the effect that they force you to think about
>> certain - possibly not obvious - properties of the code / class at hand
>> when you change the code. So while an assertion may look tricky it
>> actually helps you when modifying code to not forget important aspects.
>> This may be more tedious but it certainly helps code robustness in the
>> long run.
>>
>>> Let me put it this way: I would feel good about looking at code that had
>>> assertions in it if I saw that they were also commented where necessary,
>>> including traceability notes where that makes sense, *and* were
>>> supported by unit tests that exercised the assertions.
>>
>> I view assertions in part also as documentation. Often no additional
>> commenting is needed. I frequently have a private boolean method
>> "classInvariant" or with other (hopefully telling) name with checks and
>> has documentation of its own. In these cases you have the name of the
>> method plus documentation on the method.
>>
> I also view assertions as documentation. I consider them important
> enough in this role that I dislike casual and/or trivial use of
> assertions, because pointless assertions can obscure the role of
> genuinely important ones. Another reason why I think there ought to be
> some team guidelines on these things.

Of course, those guidelines should encapsulate the extant documentation and
articles on their correct use. It is fairly objective to evaluate whether
'assert' is used correctly. I agree with your recommendation, but it's
predicated on the guidelines avoiding stupidity. For example, it is never
correct to use 'assert' in lieu of a conventional check, say an 'if'
structure, for non-nullity of arguments to a public method.

I say this because some teams where I've worked believe that best practices
are a matter of seniority or democracy. But some pretty senior team members
I've met could have observed their own polyps directly given how far their
crania were up their viscera, and truth is not amenable to voting.

Colorful rhetoric aside, I'm simply saying that team guidelines are a good
idea to the degree that they're correct, and that correctness is discernible
in a discussion of 'assert' practices.
Message has been deleted

Robert Klemme

unread,
Jan 21, 2012, 7:25:02 AM1/21/12
to
On 20.01.2012 02:16, Arved Sandstrom wrote:
> On 12-01-16 02:55 AM, Robert Klemme wrote:
>> On 15.01.2012 22:49, Arved Sandstrom wrote:
> [ SNIP ]
>
>> Regarding the method refactoring argument: if there is so much code and
>> hence so many local variables that you want to use blocks to introduce
>> smaller scopes chances are that the logic within that blocks is also
>> largely independent from the code around so it is a good candidate for
>> refactoring anyway. The reason for refactoring into methods isn't the
>> scope but the independent logic.

> Let me give you an example. Some days prior to writing my post I had to
> write some code that processed a number of items in a similar fashion.
> Each item was a matter of 2 or 3 lines of code. In theory each process
> could have been collapsed into one very long line with multiple
> duplicated and chained method calls, rather than use temporary local
> variables, but I abhor this practice. So for clarity I kept the
> operations on each item as 2 or 3 lines of code with at least one
> temporary local variable.
>
> Although the type of the local variable was the same, the operations
> that produced it were not - they depended on the item. So any method
> that would have replaced all these individually simple simple groups of
> operations would have been either a moderately complex switch or a
> moderately complex if-else if-else structure, less easy to understand,
> and more error-prone. Furthermore, a flag would have been necessary to
> the method to indicate which branch to take.

Why _one_ method? There could be a method for each variant, couldn't
it? Chances are that the same code could be used for several items so
you end up with less methods than items.

> As you may have guessed this logic had to do with post-processing
> various String and Boolean command-line options delivered by a
> command-line processor. Quite frankly there is nothing pretty about
> this, and there never has been in any language I've ever used - all you
> can hope for is to keep the code clear, as error-free as possible, as
> change-proof as possible (one of the main reasons for me using local
> blocks actually), and just tolerate the boilerplate processing otherwise.

I agree that this boilerplate is tedious, regardless how you do it. But
I didn't guess that your description was about such a scenario. ;-)

> However, the intent of the thread was to get some feedback, and I thank
> you all for it.

You're welcome!

Arved Sandstrom

unread,
Jan 21, 2012, 9:41:13 AM1/21/12
to
There could be, sure. I'll discuss that below your second comment.

>> As you may have guessed this logic had to do with post-processing
>> various String and Boolean command-line options delivered by a
>> command-line processor. Quite frankly there is nothing pretty about
>> this, and there never has been in any language I've ever used - all you
>> can hope for is to keep the code clear, as error-free as possible, as
>> change-proof as possible (one of the main reasons for me using local
>> blocks actually), and just tolerate the boilerplate processing otherwise.
>
> I agree that this boilerplate is tedious, regardless how you do it. But
> I didn't guess that your description was about such a scenario. ;-)
[ SNIP ]

There are a number of Java command line option parsers available; I
happen to like JArgs which is GNU getopt compatible.

Your first step after defining your options and running the parser on
actual arguments is to retrieve raw option values. JArgs is not generic,
so the retrieved option values are retrieved as Objects although they
are actually Strings or Booleans or Doubles or Integers or Longs.
Depending on how many of these types are in use in your situation, if
you were going to have convenience methods at all you'd have one for
each datatype involved in your options.

Many or some of your convenience methods might accept an option default
parameter, to be passed on to the appropriate JArgs getOption method.
This shouldn't multiply the number of methods that you've created.

I'm not going to deliberately complicate things so as to scupper your
argument, but in the case of the processing I was doing at this stage,
some of the String option values could only have certain values (they
referred to input and output formats, actually). I have enums defined
for this purpose, so for some of the String options the retrieved values
were immediately converted to enum instances. Other Strings were
freeform so no such processing was appropriate.

That's another method right there, at a minimum. Let us say one extra.

Similarly, a couple of the String options represented file names. Rather
than set them as generic Strings into my own "command line options"
object, I wanted them to be Files. Null is not an acceptable value for
the java.io.File ctor, so at the very least I had to look for null for
_these_ particular String options; "" is OK for java.io.File but it's
not OK for my app.

Hence a bit of specialized "String options meant to be filenames"
processing for some options.

This would/could be an extra convenience method of its own.

In summary, looking at my actual application command line options
(including which option datatypes I actually use), something like a
dozen of them [1], one could create half a dozen convenience methods
that would be used instead.

I don't think I can credibly argue that using the methods would be
worse. I am just not convinced it would be better. :-)

AHS

1. I think the number of options I have is justified. I probably could
have reasonably added a couple more. I've been using getopt and GNU
enhanced getopt and shell getopts for well over 20 years. When I first
encountered these beasts, after going through the usual exercise of
writing my own C.L. handling in C, I'll admit to having gone overboard.
But I'd like to think I am more sensible now: good command line design
is based on lots of usability experience with a dash of artistry.

Robert Klemme

unread,
Jan 22, 2012, 7:03:32 AM1/22/12
to
On 21.01.2012 15:41, Arved Sandstrom wrote:
> On 12-01-21 08:25 AM, Robert Klemme wrote:
>> On 20.01.2012 02:16, Arved Sandstrom wrote:
>>> On 12-01-16 02:55 AM, Robert Klemme wrote:
>>>> On 15.01.2012 22:49, Arved Sandstrom wrote:

>> I agree that this boilerplate is tedious, regardless how you do it. But
>> I didn't guess that your description was about such a scenario. ;-)

> In summary, looking at my actual application command line options
> (including which option datatypes I actually use), something like a
> dozen of them [1], one could create half a dozen convenience methods
> that would be used instead.
>
> I don't think I can credibly argue that using the methods would be
> worse. I am just not convinced it would be better. :-)

Fair enough.

> But I'd like to think I am more sensible now: good command line design
> is based on lots of usability experience with a dash of artistry.

I'd say this is true for so many areas of software engineering. :-)

Thank you for the elaborate explanation!

Arne Vajhøj

unread,
Feb 6, 2012, 9:24:01 PM2/6/12
to
On 1/20/2012 9:32 PM, Stefan Ram wrote:
> r...@zedat.fu-berlin.de (Stefan Ram) writes:
>> alpha();
>> { /* add a button to the frame */
>> final Button button = new Button();
>> frame.add( button ); }
>> beta();
>
> I forgot to mention that there is an old software-engineering
> principle: »The scope of every identifier should be as small
> as possible.« Blocks help to realize this.
>
> Or, let's look at code posted into some other thread recently:
>
> student<freeno...@gmail.com> writes:
>> GOval g = makeCircle(centerX, centerY,radiusOuterCircle ,
>> Color.RED);
>> add(g);
>> g = makeCircle(centerX, centerY,radiusMiddleCircle ,
>> Color.WHITE);
>> add(g);
>> g = makeCircle(centerX, centerY,radiusInnerCircle ,
>> Color.RED);
>> add(g);
>
> With blocks, »g« can be made final:
>
> { final GOval g = makeCircle( centerX, centerY, radiusOuterCircle, Color.RED ); add( g ); }
> { final GOval g = makeCircle( centerX, centerY, radiusMiddleCircle, Color.WHITE ); add( g ); }
> { final GOval g = makeCircle( centerX, centerY, radiusInnerCircle, Color.RED ); add( g ); }
>
> this also is more beautiful, because now there is more
> symmetry between the the three actions, which then allows a
> possible refactor to:
>
> { final CircleMaker circleMaker = new CircleMaker( g, centerX, centerY );
> circleMaker.make( radiusOuterCircle, Color.RED );
> circleMaker.make( radiusMiddleCircle, Color.WHITE );
> circleMaker.make( radiusInnerCircle, Color.RED ); }
>
> (this will probably not solve the actual problem of »student«).
>
> Or, to tell the story from its end:
>
> The most important principle is »DRY« - »Don't repeat
> yourself!«. To do this, we abstract repetitions of the same
> principle into a single code location using abstractions.
> But to do this, in turn, we need to be able to see
> repetitions of the same principle. And to be able to see
> them, the code needs to be made as symmetric as possible,
> that is, to do the same thing, the same wording should be
> used.
>
> Or in a single line:
> First, make the repetition obvious, then abstract it.

The rule is OK.

But I consider it a 75% rule. Follow it in 75% of cases
and skip it when it does not make sense.

In this case I think the code became less readable, so I would
not do it.

And I would certainly not do that refactoring as it obfuscates
what the code is doing by hiding the adding to g.

Arne


0 new messages