 |
About iterative control abstraction
Posted by forax on October 04, 2006 at 12:11 PM | Comments (17)
Neal proposes to use for to tag methods that take
a synchronous closure as parameter and to call this new kind
of method.
It's better than to use synchronized
as proposed before but (there is always a but :) i see two drawbacks.
First, for is used to tag the whole method
and not one of its parameter
so there is no way to define a method that
takes a synchronous closure and an asynchronous one.
Second, in Java, for is an instruction and not
an expression but synchronous method may return a value.
int sum=for each(int sum,Integer value:Arrays.asList(2,3),0) {
sum+value
}
...
Else, there is a bug in signature of the method
eachEntry proposed by Neal.
He uses the syntax of the closure v0.2
and as i was explained here if you don't use function type,
you have to care about subtyping relationship
between parametrized types.
The code above is not legal with the signature given by Neal
void for eachEntry(Map<K,V> map, Block2<K,V,E> block) throws E.
Map<String,Droid> map=...
for eachEntry(CharSequence droidName, Droid droid : map) {
...
}
The type of droidName must be the same
than the first type argument of the map, here String and
not CharSequence.
The method signature eachEntry must be changed to :
public interface Block2<K,V,throws E> {
void invoke(K k, V v) throws E;
}
public static <K,V,throws E>
void for eachEntry(Map<K,V> map, Block2<? super K,? super V,E> block) throws E {
for (Map.Entry<K,V> entry : map.entrySet()) {
block.invoke(entry.getKey(), entry.getValue());
}
}
I still prefer the closure v0.1, i think dispite the fact that
it introduce a new type (function type), it's simpler to read.
The method each of my first example with
the v0.2 is coded like this:
public interface Expr1<V,R> {
R invoke(V v,R r);
}
public static <R,V>
R for each(Collection<? extends V> values,R initialValue,
Expr1<R,? super V> expr) {
for(V value:values)
initialValue=expr1.invoke(value,initialValue);
return initialValue;
}
and with v0.1 :
public static <R,V>
R each(Collection<V> values,R initialValue,R(V v,R R) expr) {
for(V value:values)
initialValue=expr1(value,initialValue);
return initialValue;
}
Rémi
Bookmark blog post: del.icio.us Digg DZone Furl Reddit
Comments
Comments are listed in date ascending order (oldest first) | Post Comment
-
I think we should also rename Java to Java++. Maybe even J++, or jC++ with the j being optional? ;-)
The trap door is there, everybody knows about it and where it is, yet Java is firmly on the way straight towards it...
Cheers,
Mikael
Posted by: mikaelgrev on October 04, 2006 at 12:32 PM
-
Why? Why? Why? Why all this complexity? Besides a nice theoretical discussion, do you really believe that it should be a part of Java, in any incarnation (v0.1 or v0.2)? Do we really have to scare people away from Java and make maintenance of someone else's code (who thought that he was very clever to use the new bells and whistles) a real nightmare?
Posted by: kirillcool on October 04, 2006 at 01:40 PM
-
I liked the idea of closures until I saw the syntax (all proposed variants)... I'm frankly unsure that a line such as:
R each(Collection values,R initialValue,(R)(V v,R R) expr) {
...is readable or maintainable. The Java language has always been one of the most readable out there, and while generics clutters things up a bit, it's still good. Closures in the Java language are a step too far though, and better left in the domain of specialized scripting languages for the JVM (as scripting generally reduces typesafe declarations etc so the closure syntax isn't so heavyweight and unreadable).
Much syntax sugar is irrelevant as the language is very expressive and IDEs fill in the gaps effectively.
- Chris
Posted by: chris_e_brown on October 05, 2006 at 12:36 AM
-
Rémi,
there is a simpler alternative proposal for closures here.
I think it is a good balance between readability and power.
Regards,
Xavi
Posted by: xmirog on October 05, 2006 at 01:47 AM
-
I am also very unsure whether closures will really increase readability and maintainability. I am involved in large projects where one has to use much of someone else's coding or you have to dig into or to maintain coding which has not been written by oneself. And the one who did is unavailable or several thousand miles away. I always found that the simplicity of the language makes not only its beauty but also contributed to its readability and maintainability.
Posted by: rbirenheide on October 05, 2006 at 03:41 AM
-
>> there is a simpler alternative proposal for closures here. I think it is a good balance between readability and power.
As far as I understand, it is a proposal for syntax sugar for anon-inner classes, not support for _proper_ closures. Also, the author also has removed the newlines just so that the proposal looks concise, which it in reality is not.
Anyway, as I have mentioned it before, I think it is too late for Java to include closures, as the base libraries are not made with 'closure philosphy' in mind. So closures would just look like an odd addition. I think additions to Java the language must now be restricted, otherwise it would just look clunky and inconsistent.
Best, IMO, would be if Sun starts promoting the more modern languages like Scala, which has a more consistant look and better features. Unlike Java, Scala was developed from ground-up with features that would be needed for concurrency.
Please, please, please let Java have a dignified middle-age. New additions to Java is looking like an old lady wearing mini-skirts and tongue-piercing.
Posted by: vhi on October 05, 2006 at 04:47 AM
-
Java's exceptions and generics (especially wildcards) are both scary in my opinion. And overloading has more troubles than we sometimes think, too. Think about how much nicer this stuff would look otherwise. Beyond that, CICE probably is good enough, the more this conversation goes on.
Posted by: tompalmer on October 05, 2006 at 08:56 AM
-
Remi: you misunderstood the construct. The "for" stuff is orthogonal to synchronous versus asynchronous.
Posted by: gafter on October 05, 2006 at 09:33 AM
-
Neal, If Remi missunderstood this text, that was written to make people understand it, how big of a change do you think an average Java-Joe has to understand a new semi-pros' code when he writes bugs that has to do with this syntax?
Closures are too late for Java. Please put the money and effort in the improvement and cleanup of the JDK API instead.
Cheers,
Mikael Grev
Posted by: mikaelgrev on October 05, 2006 at 10:00 AM
-
Neal, hugh ??
for -> control abstractions to act like loops -> Non-local transfer -> synchronous closure
Rémi
Posted by: forax on October 05, 2006 at 10:35 AM
-
Mikael: I didn't write anything about synchronous versus asynchronous or threads in the blog post about loop abstraction, so Remi's misunderstanding wasn't based on what I wrote.
Remi: The "for" thing is just - JUST - to cause the meaning of break and continue to link to the context of the invocation itself. Nothing more. It is possible to handle the nonlocal transfers across threads, which I will explain in a separate blog post. A concurrent loop implemented this way would have continue skip the current iteration and break would abort all uncompleted iterations. It can be done in a library without any additional language changes, and I suspect this would be a very valuable addition to java.util.concurrent.
Posted by: gafter on October 05, 2006 at 04:35 PM
-
Neal, are you 100% sure this is what Java needs?
Cheers,
Mikael
Posted by: mikaelgrev on October 06, 2006 at 12:43 AM
-
I also prefer 0.1 syntax over 0.2
Posted by: mcekovic on October 06, 2006 at 01:09 AM
-
When I read 0.1 syntax first time, I was supprised with the quality and of the proposal. The 0.1 syntah was clean and readable, everything seemed natural and fit well within Java universe.
When I read 0.2 proposal, I was confused and has feeling that 0.2 is actually step backwards. Why typing an iterface when compiler can do that for us? Why having to type 'invoke' ? Unnecesary convention. Function type seems much more natural, readable, conciese and fits well with existing Java style (strong typing). It also seems more flexible (no need to 'super' and 'extends' type parameters, no need to bother with exception types, etc...
Regarding non-local transfer I do not have definite opinion. It could be very dangerous and cause of hard-to-spot bugs, but on the other hand, it could be very powerful.
Posted by: mcekovic on October 06, 2006 at 01:19 AM
-
Maybe we should just introduce function types (which are clean and natural) with a nice proposed 0.1 syntax, but get rid of non-local transfer for keeping the things more simple?
Posted by: mcekovic on October 06, 2006 at 01:23 AM
-
me 2, I =think proposal 0.1 but a bit clear
int function(float f) ---> int(float)
proposal 0.2 takes replay heavily on the generic system, but I afraid that the existing erasing generic can handle it.
Posted by: fcmmok on October 06, 2006 at 08:32 AM
-
I also have a preference for the version with function types, but I'm trying to separate the issues for the purpose of moving the discussion forward. There are people who are OK with closures but not function types, and vice versa. Function types add a some complexity to the specification but significantly simplify programs using the constructs. Since more people are more likely to be reading programs than language specifications, it may be a better tradeoff to have function types.
Similarly for the treatment of break/continue/return, there is not universal agreement. But just to be clear: in Java the lexical environment of a block of code includes the bindings for break, continue, and return, and any proposal for closures that does not capture this part of the lexical environment is incomplete and significantly less useful than one that does.
Posted by: gafter on October 06, 2006 at 08:56 AM
|