I don't think the parent post meant that Java for OS X run only from the command line (obviously it didn't), or that it didn't support Swing (well, duh, of course it did), but that support for these things was weak -- which was certainly true.
Mr. Cornelius is right that Java has been something of a second-class citizen on OS X. Java is privileged to be a real citizen of an OS at all -- on Linux it is a sort of visiting dignitary, and on Windows it is a sort of persecuted immigrant. But OS X Java wasn't perfect: Swing apps, while they looked great, definitely didn't run as smoothly as Carbon and Cocoa apps. Applet support was mostly good, but still spotty. Apps were slow, especially UIs and graphics in general. And, of course, Java was waaaay out of date.
The new version of Java is a huge leap forward in all these problems. With this newest release, it looks much more like a "first-class" citizen than it ever did before.
Except, why should everyday consumers be the ones paying this $30 tax? The way I see it, the huge businesses throwing away 1000 486's along with CRT's, or the workers who take them home and then throw them out (initially thinking they got a great deal) are the real ones polluting.
Ummmmmm... you should pay this $30 tax because you've purchased something that will, sooner or later, be an environmental hazard. If you're a sensible and/or moderate person who only buys one computer every four years, you only pay $30 every four years. If you're a big corporation that buys 1000 CRTs, you pay $30000 for that. Seems fair to me.
The $30 figure here is open for debate -- as is the decision of whether the fee goes at purchase time or discard time (probably the former is easier to enforce, but the latter captures the actual cost better), or even directly to the manufacturer. The point is, it should be in the chain somewhere, in a uniform way for everyone, much as the costs of raw materials are in the chain now. If you introduce something into the space of economic concerns, the market should theoretically react to it. [Insert treatise on tort law here. And possibly refer to somebody who actually knows something about economics.]
Sure, for the person who's throwing the computer away. But the long-term costs in human health and environmental damage are high... or at least, if you could put a monetary value on them, I'm guessing it would be more than $30.
The trick is that there's no simple way to pass these costs back to the person who puts the computer in the dumpster. [Insert treatise on externalities here.] If you're feeling socially responsible, it's still better to recycle, and far better still to put that old machine to work in some extraodinarily geeky project which will later be featured on Slashdot.
(Speaking of which, has anybody got Linux to run on an Apple ][+ with 48k of ram yet?)
The author of the article, and the researcher about whom it's talking, don't seem to agree with your assessment of they think. Note the carefully qualified conclusion:
An explosion of art, culture and individual expression that took place in Africa between 100,000 and 50,000 years ago
may have been triggered by biological changes in the human brain, according to Richard Klein.
And a single gene? Not the researchers' claim:
Professor Klein said that a suite of language and creativity genes,
perhaps as few as ten or as many as 10,000, developed as a result of random mutations, giving rise to a new pattern of human culture.
It looks like the real upshot of the research is, "Hey, we found this one gene that seems somehow related to language and/or creativity, and even though we don't understand it completely and it's not a full explanation for anything, it's at least evidence that the human cultural explosion could have been a genetic rather than social change."
It looks like what you need to be railing against is not researchers but readers who draw absurd, overly strong conclusions.
So is there some kind of strange, dark, Mason-like secret society which causes people exposed to a sufficient amount of Lisp to think that Lisp is the One True Way, and other languages are correct only to the extent that they are completely identical to Lisp?
OK, OK, I'm just griping -- and I actually, I really like Lisp quite a lot -- but I do think that sometimes it's easy to judge by familiarity, and Lisp pundits seem especially guilty of that.
There's rarely a single One True Right Way of implementing a language feature; we really need to judge each implementation in the context of the language it's implemented in, and look for a clean, consistent, orthogonal, well-closed meshing of the feature into the language's feature set.
With that in mind, to your items:
(1) The new Java enums are not C-style enums at all (nor are they Lisp's symbols). They are a special variant of classes with a stronger class-level contract than normal classes (a fixed instance pool being the big one), an approach which works very well in an OO language with strong static typing. (For those of you following at home, Lisp is, for the most part, a dynamically typed language.)
(2) Lighten up. The for(x : c) syntax is lovely to a Java programmer's eyes, and fits the existing constructs well. Lisp's approaches, unsurprisingly, fit Lisp well, but wouldn't make much sense grafted into Java. I am glad, however, that Lisp also solves this problem. That is good to hear. Thank you for sharing.
(3) Java's original designers had two concerns: first, primitives are a potential performance gain; second, the semantics of arithmetic get sticky when integers can be null. Other language (e.g. Smalltalk) have addressed these problems reasonably well, but it's still a very debatable issue.
If I had it to do myself, I'd probably not have introduced primitive types. However, as a Java programmer, what really matters to me is that they pick an approach and make it consistent. The autoboxing JSR does a good job of adding convenience without breaking this consistency, IMO.
(4) The only similarity between Java's generics and C++'s is in the syntax. Java's generics are "true" generics in the sense that they spawn new types, and rest on polymorphism instead of a sort of specialized macro expansion. (C++'s more macro-like templates make sense for C++, where static binding would preclude many aspects of Java's approach.)
I'm not quite sure what your complaint about them not being "true" is supposed to mean. Perhaps you're worried about the runtime typing semantics of generics? If so, I'd like to see you hold your own in an argument with Gilad on the subject.
But then, what the hell do I know. I'm just a Lisp junky.
I think the answer is fairly obvious: you know a lot about Lisp, and not enough about Java to be as opinionated as you are. I know much more about Java than Lisp, and I'm sure I'm guilty of the reverse.
But I don't think I need to be an expert in either language to say that we should judge each in its own context. Does C suck because it doesn't have lambda expressions? (If you are tempted to answer yes, I hereby sentence you to writing device drivers for three years.)
The poster is a little off in calling the new feature "templates", and you're correct in calling them "generics".
Templates were C++'s way of simulating generic types. The difference is that templates are essentially macros in fancy clothing, and generate a different flavor of the class for every combination of type parameters, while generics are a much cleaner, more abstract construct, better grounded in the theory of types, which use polymorphism to achieve their genericity.
Don't know if that made any sense....
In any case, this will be a fantastic feature, and they're done a much better job with it than C++ did with templates.
Does Python actually have real distributed programming support of any kind?!
(If you're tempted to give an answer like, "Yes, it has network libs", then the answer is actually "no". If it has CORBA binding support, then we're talking!)
Humor has always been, and always will be, an essential part of coping with tragedy and horror. Look at all the jokes about death. It's also a way of approaching social taboos (death, sex, and religion cover a huge swath of all jokes). While politeness demands that we always shy away from the hard questions and unpleasant insights, humor helps us keep a sense of perspective.
I agree wholeheartedly that I do not want to hear tasteless humor which cheapens the difficulties NASA faces, the courage of astronauts, or the tragedy of these deaths or any loss of human life. But I also would not wish for laughter to be left out of our society's coming to terms with these things.
Until now, we've had a nice and concise name for lampooning this thing, as in this lovely sig I spotted the other day:
Palladium: Just where the HELL do you think you're doing today?
But this new name just doesn't have the same ring to it. How do you make up a catchy slogan -- any slogan -- containing the inconceivably awkward phrase "next-generation secure computing base"?!
The resistance needs catchy terminology, even if the Evil Empire doesn't.
I suggest, as a start, that "next-generation" is superfluous:
Microsoft secure computing base: Just where the HELL do you think you're doing today?
Perhaps even the word "base" is as well, as long as the "Microsoft" is still in there:
Microsoft secure computing: Just where the HELL do you think you're doing today?
This presents the problem, however, that people may confuse the already-meaningful phrase "secure computing" with digital rights mangling.
One safe route, perhaps, is to insist on calling it "DRM", even as that phrase takes on an increasingly negative connotation and Microsoft attempts to disown it.
Only six years, so no, I suppose not, in the grand scheme of things.
The point is that sometimes very obvious things escape even the most experienced programmers.
A few more good words
on
Effective Java
·
· Score: 5, Informative
This is a fantastic book, and anybody's who's serious about writing good Java code should study it carefully. It's one of the best-written books -- may the best -- on the practical details of programming that I've ever encountered, and the advice is gold. The section on correctly implementing equals() and hashCode() alone is almost worth the price of the book.
The reviewer complains about some of the thinner or more "obvious" items, but I disagree. Heaven only knows how many times I've wished that really good and experienced programmers follow what seems the obvious maxim: "Minimise the accessibility of classes and members."
It's true that "Know and use the libraries" seems rather obvious and vague advice, but Bloch's exposition drives home the fact that you may not follow this advice as well as you think. As always, his examples are excellent: he shows how an innocuous-seeming abuse of java.util.Random creates serious problems, and how proper use of the libraries fixes the problem. How often do you write a loop to print the contents of an array? I never realized until Bloch pointed it out that System.out.println(Arrays.asList(array)) accomplishes the same thing much more simply.
If you're a Java programmer, get this book. If you're a technical author, aspire to it.
The problem with side-by-side comparisons like this -- MacWorld is an especially egregious offender -- is that they strongly favor comparisons on quantifiable attributes, like feature matrices and benchmarks.
Unfortunately, these things aren't what users really care about.
Most any modern browser will render most any web page at a perfectly acceptable speeds. I don't really give much of a shit about rendering times, unless some browser's are so incredibly bad that I actually notice them. (Perhaps I'm more patient than some users, but honestly, I really don't care. They'll all just fine.)
What I care about is the whole "browsing experience" -- and that's hard to quantify. A program's functionality is more than the sum of its features: it also involves how well those features work together, and the smoothness of the facade under which they fit. I don't actually want a lot of features -- I want very few powerful features that give me tremendous functionality.
This bake-off misses the subtle, truly important differences that make it worth switching. For example:
OmniWeb renders pages gorgeously. They just... look better. They're easier on the eye, scan faster, read faster, and are just... pleasing. I defy even Tufte to quantify that.
OmniWeb (and, increasingly, Chimera) feel much more like OS X apps than the alternatives. They have great UIs. Apple goes a long way toward quantifying that in their HI guidelines, but really, it's a "feels good" thing.
Mozilla's tabbed browsing isn't just a feature in a checklist -- it's a wonderfully powerful and well-thought-out feature that's tightly, thoughtfully integrated with the app. Menus are keyboard shortcuts for tabs are there where you'd want them; tabs behave helpfully and sensibly. It's not the tabs that are exciting; it's the fact that they work so darned well.
Do keep trying, MacWorld. I'm glad that somebody at least acknowledges that there are alternatives!
The basic idea was neat in that it removed conscious choice from the equation....
That's not really accurate. Scheonberg was trying to force composers into thinking of sounds they wouldn't have otherwise, but for him, conscious choice was still very much a part of the picture. He was an expressionist -- meaning that he was still interested in expressing, not merely generating.
The real philosophical bullet of twelve-tone was not the removal of conscious choice... quite the opposite, in fact: it was the idea that composers could make a conscious choice of what formal musical system to follow, and in fact, one could consciously invent a whole formal system out of thin air. Prior to Schoenberg, music had been philosophically rooted in a sort quasi-religious of sense of cosmic order, and he said, "No, look, I can just make up a system! No cosmic order to it -- just conscious choice."
The aesthetic problem that 12-tone faces is that music theory is usually a model, a post-hoc way of dissecting music, more than it is a way of constructing it. Traditional "functional tonality" (Bach, Beethoven, Beatles) evolved very organically out of basic physics and human perception, and seems to resonate more easily with listeners than Schoenberg's consciously concocted system.
However, I think Scheonberg actually did a fine job of making conscious aesthetic choices that produced some excellent music. It was really other composers who took serialism to its absurdly deterministic extremes. Now Webern... Webern I find horribly cold and dry, more interesting to read on paper than hear. So there's individual taste for you!:)
This dodecahedral thing doesn't really turn my crank, but dumb old MIDI will suck the soul out of most any classically composed music... so it's had to say what it might be like with live players.
The version "1.4.1" refers to a version of the Java specification. I believe that the "_01" only refers to a patch level of Sun's implementation.
Others in this discussion are correct that Apple's JVM is at least partially based on Sun's, and Apple has in the past opted to keep their patch numbers (the bit past the underscore) correlated with Sun's, suffixing Apple-specific patch numbers to the Sun patch numbers.
However, what goes after the underscore is to some extent up to Apple -- all that matters is that they're keeping up with patches to Hotspot. So don't get too bent out of shape over the missing "_01", because you're not usually going to see it in their annoucements anyway.
Now if Apple is actually fails to keep integrating patches... that's certainly something to get bent out of shape about.
EBay has done very little to prevent abuses like this, yet they'll prevent a musician from selling his own work?!
Should eBay really be responsible for preventing these abuses? The market does handle some things well, and this is one of them: if people are willing to pay, let them pay. As long as the seller accurately represents what they are selling, and the sale doesn't break the law, the rest is between the buyer and the seller.
One time, I was hanging out with a friend, and he noted that he'd found a Susan B. Anthony silver dollar. I said, "You should sell it on eBay!" We laughed... then looked at he other, and he checked: sure enough, there were several Susan B. Anthony dollars on sale. One was bidding at over $3.
OK, so the buyers are probably suckers. But they're not being scammed -- they're just paying money for something that you and I probably think is not worth it. Is that eBay's problem?
So does this mean that I could sell software to Yahoo! with an EULA that allows me to collect statistics on which applications they use, and for how long? On broader aspects of their business's internal functioning? What about an EULA that allows my software to trap keystrokes, gather passwords, and open backdoors on their servers?
OK, so probably this Yahoo thing is blown out of proportion and context in typical Slashdot fashion. But imagine it's for real -- would an EULA like this stand if challenged? Why or why not?
I'm suggesting they could have used the target type and the signature(method name, the real types of the parameters (or super classes)
Right, but you lose all kinds of compile-time type safety if the language allows your example. Think through the static typing of your example's parse tree -- if we allowed the code you suggest, you also have to allow f(new Object()) to compile, even though there would be no matching method at runtime.
So how do you instantiate a subclass of Thinger? You write another create method.
Not necessarily -- you can have a single method that dispatches to a bunch of different constructors: return foo ? new Quux() : new Fruux();. If you have all the different subclasses in the same package, you can keep the constructors package-private.
If your subclasses are all in different packages, and you want to control instantiation within your project, I suggest you take a look at Macker (see sig).
Using the types of the arguements for the method lookup is not wacky. Haskell does it. I don't know the right words to use, but it is like polymorphism including the arguments, not just the target.
Java does use the types of the arguments. For example, the following will do what you want:
The reason the code you posted doesn't work isn't that Java doesn't use the compile-time types of the arguments to resolve overloaded functions. Rather, it's that x ? y : z is an expression, and it needs to have a single type. What is that type in your example? Do you want expressions to have a set of possible types, like {String,List}? That's what I was saying would play hell with the spec. Or do you want the expression to have the type Object, and have overloaded function resolution use runtime types? If so, you lose a lot of compile-time type checking.
The reason Haskell lets you do this is that it's much more weakly typed than Java. Personally, I like the strong typing, and I think the inconvenience here is minimal.
I guess I just have problems with static methods. This goes back to implementing alloc().init(). You can't do it with static methods.
Actually, you can. What you're looking for is the static factory method pattern. Here's an example that returns a single shared "empty instance" of a class if an argument is null or empty:
public abstract class Thinger
{
public static create(String thingerValue)
{
if(thingerValue == null || thingerValue.length() == 0)
return EMPTY_THINGER;
return new Thinger(thingerValue);
}
private static final Thinger EMPTY_THINGER = new Thinger();
private Thinger()// empty thinger ctor
{... }
private Thinger(String thingerValue)
{... }...
}
You then say Thinger.createInstance("foo") to use it. The static method takes the place of your "alloc", and the constructor is the "init". You can also use this technique to return a subclass of Thinger; give the subclass a package-private constructor if you're worried about outsiders instantiating it.
I think this does everything you want. The only problem with this technique is that you have to know that you're going to do it ahead of time -- you can't retrofit a constructor as a static factory without breaking the API.
generics
Your proxy thing is nifty at a glance. Generics are supposed to be there soon -- quite possibly in 1.5 -- and promise to be good.
Why can't I 'Object i = 5;'? There should be a 'void*' type.
You don't want a "void*" type; you just want int and the other primitives to be fully privileged objects (subtly different). This is probably the most common criticism of Java, and it's reasonable. There are also reasonable arguments for having primitives apart from objects, however. They didn't do this without some thought. Still, I lean toward your opinion on this one.
Why can't I 'Method m = Object.toString;'?
Reasonable -- it's a little shorter than Method m = Object.class.getMethod("toString", new Class[0]). But it's not a big issue -- in most cases where you'd use that, an interface paired with an anonymous inner class is more appropriate (and typesafe).
Why can't I [stuff] and get the right method called!?
Because that's a pretty wacky idea. Think for a moment about the implications of what you're proposing here -- x ? y : z is an expression...what is its type?
You could make this work, but would it be worth the hideous mess it would make of the spec to save you from having to type the words if and else?
Why can't I 'import java.util.*String*;' or 'import java.*.*;' ?
Because it poses tremendous potential namespace conflict problems with little clear benefit.
Why do we have 'new' instead of alloc and init?
Separating instantiation from initialization is reasonable; static factory methods do this just fine, but require foreknowledge of the problem. Such a facility, however, would still need to provide the guarantee that you can't actually obtain a reference to an object until it's fully initialized, which is where a naive implementation looking like like MyClass.class.alloc().init() would fail.
Why aren't static methods inherited?
Because that's an absolutely hideous idea. Static methods aren't part of the signature matching that underlies the type system, and don't participate in polymorphism; they are semantically equivalent to methods on the class, not the object (which is how Smalltalk does it).
I'd add to your list the lack of generics (which they're working on) and some of the unpleasant aspects of the memory model on multiprocessor machines.
Oh, come now. The jewel of the Java spec crown is the JLS itself -- Java's a gorgeous language (complaints from Lisp and Smalltalk purists aside), it's the language itself that won developers' hearts, and it's the language itself that underpins the good work of all the other specs.
J2EE is nobody's jewel. It's more like what C++ was about 15 years ago -- big, ugly, stinky, convoluted, overfeatured, overspecified, yet still incomplete, and works best if you just pretend that certain parts of it just don't exist... but it does the job, it's practical, and the industry's behind it. Like C++, J2EE opened up a whole world of options that were reserved for elite programmers and academic researchers before it came along (J2EE opened up distributed computing much as C++ opened up OOP).
And, like C++, in about 10 years somebody will come along with something much better that looks like the vague picture of perfection we all almost have now, something cleaner and smarter, which picks the right problems and solves them well -- something that does to J2EE what Java did to C++.
The question is, will that something in 10 years also be a specification based on the Java language? That's what I think Jason Weiss's questions may really drive at. And I'm not willing to take guess at the answer.
Now they all work for Apple?
on
Java For BeOS
·
· Score: 2
Remember--a year ago, maybe eighteen months, Be promised its users that the J2SDK for Be was done. They basically committed themselves to a pact signed in the blood of their unborn children that J2SDK would be in people's hands by that year's end.
Apparently, when Be folded, those same people went off to work at Apple -- whose Java 1.4 for OS X will be available at the end of September.
Oops. Maybe they meant September of 2007.
Actually, there's been no "blood of unborn children" pact -- Apple has been judiciously, maddeningly vague about the release of 1.4, and the September thing was only a guess from one of their project leads on a mailing list. Still, I can't help but feel that Apple did learn some lessons from the work done at Be after all....
I was considering what I'd personally want to be allowed to do.
...which is the most reasonable thing in the world. There's a real need for making licensing options a natural part of music distribution, for both the artist and consumer. I'd actually like to see an industry standard for encoding specific licensing grants (e.g. commercial use, derivative works, etc.) as a part of standard audio formats. A curious listener could just click a button in their audio player to see a track's licensing. Since audio generally doesn't come with a README, making this information part of the file format itself is essential.
Responsibility for respecting copyright ultimately falls on individual consumers -- so it seems a good idea to make that responsibility as easily and approachable as possible.
I don't see how this is newsworthy.
Then perhaps you should read a different article. Other people seem excited.
I don't think the parent post meant that Java for OS X run only from the command line (obviously it didn't), or that it didn't support Swing (well, duh, of course it did), but that support for these things was weak -- which was certainly true.
Mr. Cornelius is right that Java has been something of a second-class citizen on OS X. Java is privileged to be a real citizen of an OS at all -- on Linux it is a sort of visiting dignitary, and on Windows it is a sort of persecuted immigrant. But OS X Java wasn't perfect: Swing apps, while they looked great, definitely didn't run as smoothly as Carbon and Cocoa apps. Applet support was mostly good, but still spotty. Apps were slow, especially UIs and graphics in general. And, of course, Java was waaaay out of date.
The new version of Java is a huge leap forward in all these problems. With this newest release, it looks much more like a "first-class" citizen than it ever did before.
Except, why should everyday consumers be the ones paying this $30 tax? The way I see it, the huge businesses throwing away 1000 486's along with CRT's, or the workers who take them home and then throw them out (initially thinking they got a great deal) are the real ones polluting.
... you should pay this $30 tax because you've purchased something that will, sooner or later, be an environmental hazard. If you're a sensible and/or moderate person who only buys one computer every four years, you only pay $30 every four years. If you're a big corporation that buys 1000 CRTs, you pay $30000 for that. Seems fair to me.
Ummmmmm
The $30 figure here is open for debate -- as is the decision of whether the fee goes at purchase time or discard time (probably the former is easier to enforce, but the latter captures the actual cost better), or even directly to the manufacturer. The point is, it should be in the chain somewhere, in a uniform way for everyone, much as the costs of raw materials are in the chain now. If you introduce something into the space of economic concerns, the market should theoretically react to it. [Insert treatise on tort law here. And possibly refer to somebody who actually knows something about economics.]
The dumpster is still cheaper.
... or at least, if you could put a monetary value on them, I'm guessing it would be more than $30.
Sure, for the person who's throwing the computer away. But the long-term costs in human health and environmental damage are high
The trick is that there's no simple way to pass these costs back to the person who puts the computer in the dumpster. [Insert treatise on externalities here.] If you're feeling socially responsible, it's still better to recycle, and far better still to put that old machine to work in some extraodinarily geeky project which will later be featured on Slashdot.
(Speaking of which, has anybody got Linux to run on an Apple ][+ with 48k of ram yet?)
It looks like what you need to be railing against is not researchers but readers who draw absurd, overly strong conclusions.
So is there some kind of strange, dark, Mason-like secret society which causes people exposed to a sufficient amount of Lisp to think that Lisp is the One True Way, and other languages are correct only to the extent that they are completely identical to Lisp?
OK, OK, I'm just griping -- and I actually, I really like Lisp quite a lot -- but I do think that sometimes it's easy to judge by familiarity, and Lisp pundits seem especially guilty of that.
There's rarely a single One True Right Way of implementing a language feature; we really need to judge each implementation in the context of the language it's implemented in, and look for a clean, consistent, orthogonal, well-closed meshing of the feature into the language's feature set.
With that in mind, to your items:
(1) The new Java enums are not C-style enums at all (nor are they Lisp's symbols). They are a special variant of classes with a stronger class-level contract than normal classes (a fixed instance pool being the big one), an approach which works very well in an OO language with strong static typing. (For those of you following at home, Lisp is, for the most part, a dynamically typed language.)
(2) Lighten up. The for(x : c) syntax is lovely to a Java programmer's eyes, and fits the existing constructs well. Lisp's approaches, unsurprisingly, fit Lisp well, but wouldn't make much sense grafted into Java. I am glad, however, that Lisp also solves this problem. That is good to hear. Thank you for sharing.
(3) Java's original designers had two concerns: first, primitives are a potential performance gain; second, the semantics of arithmetic get sticky when integers can be null. Other language (e.g. Smalltalk) have addressed these problems reasonably well, but it's still a very debatable issue.
If I had it to do myself, I'd probably not have introduced primitive types. However, as a Java programmer, what really matters to me is that they pick an approach and make it consistent. The autoboxing JSR does a good job of adding convenience without breaking this consistency, IMO.
(4) The only similarity between Java's generics and C++'s is in the syntax. Java's generics are "true" generics in the sense that they spawn new types, and rest on polymorphism instead of a sort of specialized macro expansion. (C++'s more macro-like templates make sense for C++, where static binding would preclude many aspects of Java's approach.)
I'm not quite sure what your complaint about them not being "true" is supposed to mean. Perhaps you're worried about the runtime typing semantics of generics? If so, I'd like to see you hold your own in an argument with Gilad on the subject.
But then, what the hell do I know. I'm just a Lisp junky.
I think the answer is fairly obvious: you know a lot about Lisp, and not enough about Java to be as opinionated as you are. I know much more about Java than Lisp, and I'm sure I'm guilty of the reverse.
But I don't think I need to be an expert in either language to say that we should judge each in its own context. Does C suck because it doesn't have lambda expressions? (If you are tempted to answer yes, I hereby sentence you to writing device drivers for three years.)
The poster is a little off in calling the new feature "templates", and you're correct in calling them "generics".
Templates were C++'s way of simulating generic types. The difference is that templates are essentially macros in fancy clothing, and generate a different flavor of the class for every combination of type parameters, while generics are a much cleaner, more abstract construct, better grounded in the theory of types, which use polymorphism to achieve their genericity.
Don't know if that made any sense....
In any case, this will be a fantastic feature, and they're done a much better job with it than C++ did with templates.
Does Python actually have real distributed programming support of any kind?!
(If you're tempted to give an answer like, "Yes, it has network libs", then the answer is actually "no". If it has CORBA binding support, then we're talking!)
Humor has always been, and always will be, an essential part of coping with tragedy and horror. Look at all the jokes about death. It's also a way of approaching social taboos (death, sex, and religion cover a huge swath of all jokes). While politeness demands that we always shy away from the hard questions and unpleasant insights, humor helps us keep a sense of perspective.
I agree wholeheartedly that I do not want to hear tasteless humor which cheapens the difficulties NASA faces, the courage of astronauts, or the tragedy of these deaths or any loss of human life. But I also would not wish for laughter to be left out of our society's coming to terms with these things.
Not all jokes are tasteless jokes.
If the humanities majors stop talking to the math/sci/engineering majors, then tens of thousands of programmers will end up spelling like CmdrTaco!!
(Sorry, Rob. We're a bunch of ruthless ingrates here, I know.)
But this new name just doesn't have the same ring to it. How do you make up a catchy slogan -- any slogan -- containing the inconceivably awkward phrase "next-generation secure computing base"?!
The resistance needs catchy terminology, even if the Evil Empire doesn't.
I suggest, as a start, that "next-generation" is superfluous: Perhaps even the word "base" is as well, as long as the "Microsoft" is still in there: This presents the problem, however, that people may confuse the already-meaningful phrase "secure computing" with digital rights mangling.
One safe route, perhaps, is to insist on calling it "DRM", even as that phrase takes on an increasingly negative connotation and Microsoft attempts to disown it.
You know you're a geek when you get excited about the release of new fonts.
No kidding.
Of course, if I were posting this from a Linux machine, I wouldn't be excited, because I wouldn't be able to fucking read the story.
You aren't very long into Java, are you?
Only six years, so no, I suppose not, in the grand scheme of things.
The point is that sometimes very obvious things escape even the most experienced programmers.
This is a fantastic book, and anybody's who's serious about writing good Java code should study it carefully. It's one of the best-written books -- may the best -- on the practical details of programming that I've ever encountered, and the advice is gold. The section on correctly implementing equals() and hashCode() alone is almost worth the price of the book.
The reviewer complains about some of the thinner or more "obvious" items, but I disagree. Heaven only knows how many times I've wished that really good and experienced programmers follow what seems the obvious maxim: "Minimise the accessibility of classes and members."
It's true that "Know and use the libraries" seems rather obvious and vague advice, but Bloch's exposition drives home the fact that you may not follow this advice as well as you think. As always, his examples are excellent: he shows how an innocuous-seeming abuse of java.util.Random creates serious problems, and how proper use of the libraries fixes the problem. How often do you write a loop to print the contents of an array? I never realized until Bloch pointed it out that System.out.println(Arrays.asList(array)) accomplishes the same thing much more simply.
If you're a Java programmer, get this book. If you're a technical author, aspire to it.
The problem with side-by-side comparisons like this -- MacWorld is an especially egregious offender -- is that they strongly favor comparisons on quantifiable attributes, like feature matrices and benchmarks.
... look better. They're easier on the eye, scan faster, read faster, and are just ... pleasing. I defy even Tufte to quantify that.
Unfortunately, these things aren't what users really care about.
Most any modern browser will render most any web page at a perfectly acceptable speeds. I don't really give much of a shit about rendering times, unless some browser's are so incredibly bad that I actually notice them. (Perhaps I'm more patient than some users, but honestly, I really don't care. They'll all just fine.)
What I care about is the whole "browsing experience" -- and that's hard to quantify. A program's functionality is more than the sum of its features: it also involves how well those features work together, and the smoothness of the facade under which they fit. I don't actually want a lot of features -- I want very few powerful features that give me tremendous functionality.
This bake-off misses the subtle, truly important differences that make it worth switching. For example:
OmniWeb renders pages gorgeously. They just
OmniWeb (and, increasingly, Chimera) feel much more like OS X apps than the alternatives. They have great UIs. Apple goes a long way toward quantifying that in their HI guidelines, but really, it's a "feels good" thing.
Mozilla's tabbed browsing isn't just a feature in a checklist -- it's a wonderfully powerful and well-thought-out feature that's tightly, thoughtfully integrated with the app. Menus are keyboard shortcuts for tabs are there where you'd want them; tabs behave helpfully and sensibly. It's not the tabs that are exciting; it's the fact that they work so darned well.
Do keep trying, MacWorld. I'm glad that somebody at least acknowledges that there are alternatives!
The basic idea was neat in that it removed conscious choice from the equation....
... quite the opposite, in fact: it was the idea that composers could make a conscious choice of what formal musical system to follow, and in fact, one could consciously invent a whole formal system out of thin air. Prior to Schoenberg, music had been philosophically rooted in a sort quasi-religious of sense of cosmic order, and he said, "No, look, I can just make up a system! No cosmic order to it -- just conscious choice."
... Webern I find horribly cold and dry, more interesting to read on paper than hear. So there's individual taste for you! :)
... so it's had to say what it might be like with live players.
That's not really accurate. Scheonberg was trying to force composers into thinking of sounds they wouldn't have otherwise, but for him, conscious choice was still very much a part of the picture. He was an expressionist -- meaning that he was still interested in expressing, not merely generating.
The real philosophical bullet of twelve-tone was not the removal of conscious choice
The aesthetic problem that 12-tone faces is that music theory is usually a model, a post-hoc way of dissecting music, more than it is a way of constructing it. Traditional "functional tonality" (Bach, Beethoven, Beatles) evolved very organically out of basic physics and human perception, and seems to resonate more easily with listeners than Schoenberg's consciously concocted system.
However, I think Scheonberg actually did a fine job of making conscious aesthetic choices that produced some excellent music. It was really other composers who took serialism to its absurdly deterministic extremes. Now Webern
This dodecahedral thing doesn't really turn my crank, but dumb old MIDI will suck the soul out of most any classically composed music
The version "1.4.1" refers to a version of the Java specification. I believe that the "_01" only refers to a patch level of Sun's implementation.
... that's certainly something to get bent out of shape about.
Others in this discussion are correct that Apple's JVM is at least partially based on Sun's, and Apple has in the past opted to keep their patch numbers (the bit past the underscore) correlated with Sun's, suffixing Apple-specific patch numbers to the Sun patch numbers.
However, what goes after the underscore is to some extent up to Apple -- all that matters is that they're keeping up with patches to Hotspot. So don't get too bent out of shape over the missing "_01", because you're not usually going to see it in their annoucements anyway.
Now if Apple is actually fails to keep integrating patches
EBay has done very little to prevent abuses like this, yet they'll prevent a musician from selling his own work?!
... then looked at he other, and he checked: sure enough, there were several Susan B. Anthony dollars on sale. One was bidding at over $3.
Should eBay really be responsible for preventing these abuses? The market does handle some things well, and this is one of them: if people are willing to pay, let them pay. As long as the seller accurately represents what they are selling, and the sale doesn't break the law, the rest is between the buyer and the seller.
One time, I was hanging out with a friend, and he noted that he'd found a Susan B. Anthony silver dollar. I said, "You should sell it on eBay!" We laughed
OK, so the buyers are probably suckers. But they're not being scammed -- they're just paying money for something that you and I probably think is not worth it. Is that eBay's problem?
So does this mean that I could sell software to Yahoo! with an EULA that allows me to collect statistics on which applications they use, and for how long? On broader aspects of their business's internal functioning? What about an EULA that allows my software to trap keystrokes, gather passwords, and open backdoors on their servers?
OK, so probably this Yahoo thing is blown out of proportion and context in typical Slashdot fashion. But imagine it's for real -- would an EULA like this stand if challenged? Why or why not?
Calling all IANALs....
I'm suggesting they could have used the target type and the signature(method name, the real types of the parameters (or super classes)
Right, but you lose all kinds of compile-time type safety if the language allows your example. Think through the static typing of your example's parse tree -- if we allowed the code you suggest, you also have to allow f(new Object()) to compile, even though there would be no matching method at runtime.
So how do you instantiate a subclass of Thinger? You write another create method.
Not necessarily -- you can have a single method that dispatches to a bunch of different constructors: return foo ? new Quux() : new Fruux();. If you have all the different subclasses in the same package, you can keep the constructors package-private.
If your subclasses are all in different packages, and you want to control instantiation within your project, I suggest you take a look at Macker (see sig).
Using the types of the arguements for the method lookup is not wacky. Haskell does it. I don't know the right words to use, but it is like polymorphism including the arguments, not just the target.
// empty thinger ctor ... }
... } ...
Java does use the types of the arguments. For example, the following will do what you want:
Object f(String s) {something(s);}
Object f(List l) {somethingelse(l);}
void main(String [] a) {
if(a.length == 1)
f(a[0]);
else
f(Arrays.asList(a));
}
The reason the code you posted doesn't work isn't that Java doesn't use the compile-time types of the arguments to resolve overloaded functions. Rather, it's that x ? y : z is an expression, and it needs to have a single type. What is that type in your example? Do you want expressions to have a set of possible types, like {String,List}? That's what I was saying would play hell with the spec. Or do you want the expression to have the type Object, and have overloaded function resolution use runtime types? If so, you lose a lot of compile-time type checking.
The reason Haskell lets you do this is that it's much more weakly typed than Java. Personally, I like the strong typing, and I think the inconvenience here is minimal.
I guess I just have problems with static methods. This goes back to implementing alloc().init(). You can't do it with static methods.
Actually, you can. What you're looking for is the static factory method pattern. Here's an example that returns a single shared "empty instance" of a class if an argument is null or empty:
public abstract class Thinger
{
public static create(String thingerValue)
{
if(thingerValue == null || thingerValue.length() == 0)
return EMPTY_THINGER;
return new Thinger(thingerValue);
}
private static final Thinger EMPTY_THINGER = new Thinger();
private Thinger()
{
private Thinger(String thingerValue)
{
}
You then say Thinger.createInstance("foo") to use it. The static method takes the place of your "alloc", and the constructor is the "init". You can also use this technique to return a subclass of Thinger; give the subclass a package-private constructor if you're worried about outsiders instantiating it.
I think this does everything you want. The only problem with this technique is that you have to know that you're going to do it ahead of time -- you can't retrofit a constructor as a static factory without breaking the API.
generics
Your proxy thing is nifty at a glance. Generics are supposed to be there soon -- quite possibly in 1.5 -- and promise to be good.
Why can't I 'Object i = 5;'? There should be a 'void*' type.
You don't want a "void*" type; you just want int and the other primitives to be fully privileged objects (subtly different). This is probably the most common criticism of Java, and it's reasonable. There are also reasonable arguments for having primitives apart from objects, however. They didn't do this without some thought. Still, I lean toward your opinion on this one.
Why can't I 'Method m = Object.toString;'?
Reasonable -- it's a little shorter than Method m = Object.class.getMethod("toString", new Class[0]). But it's not a big issue -- in most cases where you'd use that, an interface paired with an anonymous inner class is more appropriate (and typesafe).
Why can't I [stuff] and get the right method called!?
Because that's a pretty wacky idea. Think for a moment about the implications of what you're proposing here -- x ? y : z is an expression...what is its type?
You could make this work, but would it be worth the hideous mess it would make of the spec to save you from having to type the words if and else?
Why can't I 'import java.util.*String*;' or 'import java.*.*;' ?
Because it poses tremendous potential namespace conflict problems with little clear benefit.
Why do we have 'new' instead of alloc and init?
Separating instantiation from initialization is reasonable; static factory methods do this just fine, but require foreknowledge of the problem. Such a facility, however, would still need to provide the guarantee that you can't actually obtain a reference to an object until it's fully initialized, which is where a naive implementation looking like like MyClass.class.alloc().init() would fail.
Why aren't static methods inherited?
Because that's an absolutely hideous idea. Static methods aren't part of the signature matching that underlies the type system, and don't participate in polymorphism; they are semantically equivalent to methods on the class, not the object (which is how Smalltalk does it).
I'd add to your list the lack of generics (which they're working on) and some of the unpleasant aspects of the memory model on multiprocessor machines.
J2EE, the jewel of the Java specification crown
... but it does the job, it's practical, and the industry's behind it. Like C++, J2EE opened up a whole world of options that were reserved for elite programmers and academic researchers before it came along (J2EE opened up distributed computing much as C++ opened up OOP).
Oh, come now. The jewel of the Java spec crown is the JLS itself -- Java's a gorgeous language (complaints from Lisp and Smalltalk purists aside), it's the language itself that won developers' hearts, and it's the language itself that underpins the good work of all the other specs.
J2EE is nobody's jewel. It's more like what C++ was about 15 years ago -- big, ugly, stinky, convoluted, overfeatured, overspecified, yet still incomplete, and works best if you just pretend that certain parts of it just don't exist
And, like C++, in about 10 years somebody will come along with something much better that looks like the vague picture of perfection we all almost have now, something cleaner and smarter, which picks the right problems and solves them well -- something that does to J2EE what Java did to C++.
The question is, will that something in 10 years also be a specification based on the Java language? That's what I think Jason Weiss's questions may really drive at. And I'm not willing to take guess at the answer.
Remember--a year ago, maybe eighteen months, Be promised its users that the J2SDK for Be was done. They basically committed themselves to a pact signed in the blood of their unborn children that J2SDK would be in people's hands by that year's end.
Apparently, when Be folded, those same people went off to work at Apple -- whose Java 1.4 for OS X will be available at the end of September.
Oops. Maybe they meant September of 2007.
Actually, there's been no "blood of unborn children" pact -- Apple has been judiciously, maddeningly vague about the release of 1.4, and the September thing was only a guess from one of their project leads on a mailing list. Still, I can't help but feel that Apple did learn some lessons from the work done at Be after all....
...which is the most reasonable thing in the world. There's a real need for making licensing options a natural part of music distribution, for both the artist and consumer. I'd actually like to see an industry standard for encoding specific licensing grants (e.g. commercial use, derivative works, etc.) as a part of standard audio formats. A curious listener could just click a button in their audio player to see a track's licensing. Since audio generally doesn't come with a README, making this information part of the file format itself is essential.
Responsibility for respecting copyright ultimately falls on individual consumers -- so it seems a good idea to make that responsibility as easily and approachable as possible.