Follow Slashdot stories on Twitter

 



Forgot your password?
typodupeerror
×
Java Microsoft Programming IT Technology

Hejlsberg Talk About Generics in C# and Java 128

An anonymous reader writes "artima.com has a very interesting interview with Anders Hejlsberg - the Borland guy now at Microsoft who can best be defined as MR C# - doing all the stuff that Borland wouldn't let him do. He discusses generics in C#, Java (1.5) and C++. Naturally there is the chance of bias but he does raise some interesting points againt Java's generics. Specifically that Java's genericised collections will have to box all primitive types as full objects, whereas C# does not. This is a big performance plus for C#. Java created the primitive types in the first place to address performance concerns but appears to be stepping sideways here. I can't help wondering if Sun has taken this approach to get the syntatic sugar in the language without requiring a bytecode change, but perhaps in a future VM version will allow primitive generics (obvioulsy forcing a bytecode regeneration)?"
This discussion has been archived. No new comments can be posted.

Hejlsberg Talk About Generics in C# and Java

Comments Filter:
  • Can't Believe (Score:2, Informative)

    by Apreche ( 239272 ) on Wednesday January 28, 2004 @01:37PM (#8114193) Homepage Journal
    People complain about the dumbest things. I always laugh when someone complains about the performance of java. Guess what, if your app needs to be high performance, you shouldn't be doing it in java. If it doesn't need to be high performance but it needs to run on every os and computing device under the sun, then you should use java.

    Programming languages are tools. Hammers for nails, screwdrivers for screws, C for hardcore big stuff and python/perl for everyday fun. Java was never intended to be high performance. It was intended to let you run a program on every single device and operating system there is, and have it run almost identically. The fact that java is as high performance as it is now is amazing. If you need performance and java isn't cutting it maybe you should ask yourself "why am I using a screwdriver to put a nail in this piece of wood?"

    As for the specific issue of genericising and java's collections. I think java's collections rule. Sure you can't make a collection of primitive types, big deal. You can make an array of primitive types. And you can even make your own class, which inherits from collection and is in fact, a collection of primitive types. But just about everything in java is an Object anyway. So an ArrayList or a LinkedList are good enough 99% of the time. You keep on coding in C#, and when the world doesn't use windows anymore we'll see if your app is still around.
  • by Matt2000 ( 29624 ) on Wednesday January 28, 2004 @01:42PM (#8114248) Homepage
    I read the article to see what the numbers were on performance differences. Turns out there were none, what a surprise! So as usual, in theory, perhaps maybe there might be a performance difference and maybe it might be significant or not, or both. Until real comparisons are made, safe to ignore.

    What's more important is his other problem with Java generics which is that in runtime it's not possible to tell what type a collection is compiled as, this is to retain bytecode compatibility. So reflection will have no clue on any of this generics stuff, which isn't a deal breaker, it's just a downside I hadn't heard about before.
  • by sab39 ( 10510 ) on Wednesday January 28, 2004 @03:06PM (#8115118) Homepage
    It doesn't have anything to do with autoboxing in Java, but it has everything to do with boxing in Java versus C#.

    Both C# and Java require boxing if you want to put an int into an object variable. They differ in whether that boxing is automatic or not (at least until Java makes it automatic in 1.5), but that's irrelevant: it still happens, so the performance impact is the same in both languages.

    However, if you're trying to put that same int into an ArrayList<int>, the two languages are very different.

    In Java, ArrayList<int> is really just ArrayList<Object> under the covers, and stores its contents into an array of type Object[], so the boxing operation still needs to happen. Hence, there's a performance hit.

    In C#, ArrayList<int> is interpreted as such at the runtime level and the JIT compiler creates native code for it that stores the contents in an array of type int[]. When you store values into that array, no boxing is needed, automatic or otherwise. No performance hit.

    Both C# 1.1 and Java 1.4 collections can hold primitive types if you box them. In Java 1.5, you get some extra syntactic sugar (which C# had from day one) but the boxing still happens. In C# 2.0, generic collections can hold primitive types without boxing. That's the difference that he's trying to get across in this article, and why it's specific to generics.

    All of this is explained very clearly in the article and it amazes me that so many people can't grasp it...
  • by sab39 ( 10510 ) on Wednesday January 28, 2004 @04:53PM (#8116482) Homepage
    I'm afraid you are wrong.

    While "int" is treated "as if" it were an Object in the CLR, and behaves as if it was a subclass of Object, it really is a value type: It's allocated on the stack, cannot be subclassed, and is passed by value when it's used as a method parameter or return value.

    The same goes for all the other built in primitive types (float, decimal, double, long, short, bool, char etc), along with user-defined Structs and Enums. These are all considered "Value Types" in the CLR.

    When instances of value types need to be treated as Objects, they are boxed, just like in Java, except that it's transparent and automatic and there's no separate class that represents the boxed type - the distinction Java makes between int and Integer simply doesn't exist in C#. (System.Int32 is just an alias for int and isn't equivalent to Integer at all in any way).

    The article clearly states that in Generic C#, the JIT actually creates specialized binary code whenever a generic class is instantiated with a value type argument. It even uses the example of List<int> turning into int[] (remember value types like int can't be subclassed, so the subclass problem doesn't arise).

    C# provides the "illusion" of no primitives, but it's certainly not true that everything's always boxed. It just provides a more elegant and flexible model of boxing than Java does.
  • Re:Boxing in Java (Score:2, Informative)

    by Steveftoth ( 78419 ) on Wednesday January 28, 2004 @07:56PM (#8118880) Homepage
    My bad, I should to have said that a Generic List is compiled at runtime into a seperate class by the JIT.

    Since in .NET CLR a List is actually compiled into a list that only holds ints (and not objects), it actually has a completly different codepath then a List or List.

    WTF are you talking about? The only way you're going to get an instance of a class that implements IList and only holds ints is to do this ArrayList intList = new ArrayList(); If you just choose ArrayList myList = new ArrayList(); you get a non-specialized version of the IList-supporting class. Me thinks you don't know what you're talking about.

    Here's what I'm talking about from the second page of the article, Hejlsberg says that there will be lots of class definitions floating around in memory.

    Bill Venners: How do generics work in C#?

    Anders Hejlsberg: In C# without generics, you are basically able to say class List {...}. In C# with generics, you can say class List {...}, where T is the type parameter. Within List you can use T as if it were a type. When it actually comes time to create a List object, you say List or List. You construct new types from that List, and it is truly as if your type arguments get substituted for the type parameter. All of the Ts become ints or Customers, you don't have to downcast, and there is strong type checking everywhere.

    In the CLR [Common Language Runtime], when you compile List, or any other generic type, it compiles down to IL [Intermediate Language] and metadata just like any normal type. The IL and metadata contains additional information that knows there's a type parameter, of course, but in principle, a generic type compiles just the way that any other type would compile. At runtime, when your application makes its first reference to List, the system looks to see if anyone already asked for List. If not, it feeds into the JIT the IL and metadata for List and the type argument int. The JITer, in the process of JITing the IL, also substitutes the type parameter.

    Bruce Eckel: So it's instantiating at runtime.

    Anders Hejlsberg: It's instantiating at runtime, exactly. It's producing native code specifically for that type at the point it is needed. And literally when you say List, you will get a List of int. If the code in the generic type uses an array of T, that becomes an array of int.

Stellar rays prove fibbing never pays. Embezzlement is another matter.

Working...