Bitten by the lambda parameter name
Zhong Yu
zhong.j.yu at gmail.com
Fri Sep 6 15:17:58 PDT 2013
Note that this problem does not only exist for lambda parameters, but
also for local variables in lambda body, apparently from the same
rationale.
void test()
{
int x = 0;
Runnable r = ()->{
int x = 1; // error: variable x is already defined
};
}
I would imagine that people are going to use deeply nested lambda
expressions, e.g. a DSL to define an html tree. This restriction is
going to become an inconvenience.
Perhaps the restriction can be limited to implicit lambda parameter
only; explicit lambda parameter and lambda body variable have less
chance of causing confusion because of the full form of declaration.
void test()
{
String s = null;
int x = 0;
Consumer<String> consumer = (String s)->{
int x = 1;
};
}
Back to Remi's original example, if we use explicitly typed parameter
Kind kind = ...
map.computeIfAbsent(kind, (Kind kind)->{...});
it looks pretty clear that a function object is being defined; readers
are unlikely to confuse `kind` the method parameter with `kind` the
local variable (which is
Stephen Colebourne's point)
Zhong Yu
On Thu, Jul 18, 2013 at 5:34 PM, John Rose <john.r.rose at oracle.com> wrote:
> On Jul 17, 2013, at 9:48 AM, Zhong Yu <zhong.j.yu at gmail.com> wrote:
>
> I personally don't think it's a strong enough case; when I read
> x->++x, I'll see this is a new x, and the new x is being incremented.
>
>
> Many of the Java language safety rules (including local shadowing rules) are
> not designed for the people on this mailing list. They are designed for the
> other 99% of programmers, who are not so eager to process language corner
> cases. And shadowing, however natural its logic is, gets experienced as a
> corner case, often enough to cause bugs in the field. (No I don't have
> survey numbers.)
>
> The value of anti-shadowing rules is less when declarations are more visible
> and/or can be placed in fewer syntactic locations. This is why class
> members can participate in shadowing: Class members generally occupy their
> own lines of code. Parameters and locals are often declared inside other
> constructs (method headers, for loops), so they are harder to see.
> Therefore, multiple competing definitions of these constructs are more
> confusing. Guess which category lambda parameters fall in? Hint: A lambda
> parameter declaration can be one token long, and embedded in an expression.
>
> So, regardless of how it outrages syntax-savvy users, I think it is better
> to forbid having lambda parameters participate in shadowing.
>
> The two proposed use cases of (foo) -> (expr_not_containing_foo) seem
> especially wrong-headed to me. Why *must* we allow users to have the exact
> name "foo", for a variable that isn't even used? Because it is so important
> to insert a clever comment that the formal parameter "foo" (though unused)
> is known to the programmer to have the same value as an uplevel variable
> named "foo"? There are other ways to comment code than choose a name for an
> unused variable!
>
> — John
More information about the lambda-dev
mailing list