Scalable Nonblocking Data Structures
An anonymous reader writes "InfoQ has an interesting writeup of Dr. Cliff Click's work on developing highly concurrent data structures for use on the Azul hardware (which is in production with 768 cores), supporting 700+ hardware threads in Java. The basic idea is to use a new coding style that involves a large array to hold the data (allowing scalable parallel access), atomic update on those array words, and a finite-state machine built from the atomic update and logically replicated per array word. The end result is a coding style that has allowed Click to build 2.5 lock-free data structures that also scale remarkably well."
why are there fewer than 1 thread per core? It says 768 cores, but only 700 threads. Does it need the rest of the cores just to manage the large number of threads?
Damn_registrars has no butt-hole. Damn_registrars has no use for a butt-hole.
It means that the atomic operation required for lock-free data structures are now available for Java from this vendor. Welcome to 1988!
The compare-and-swap approach is backed up by academic research: http://www.cl.cam.ac.uk/TechReports/UCAM-CL-TR-579.pdf [Practical Lock Freedom]
Google Talk by the author.
If brevity is the soul of wit, then how does one explain Twitter?
1988? Atomic?
Is this something to do with a Blondie tour?
AT&ROFLMAO
Click gave a Google Tech Talk last year on his lock-free hashtable as part of the 'advanced topics in programming languages' series. The one hour talk is available on Google Video here: http://video.google.com/videoplay?docid=2139967204534450862 .
700 threads in C++? Why not use assembler, actually optimize the hell out of the code, and get it down considerably. Or get a lot more done per thread.
Or... is this just a way to avoid having to get the really, really good coders who are more costly than the burn-bags?
Before, data structures would only perform well in 50-100 threads. With this work, he has it up to over 700 threads, but it hasn't been load tested yet. There's a good chance that he's on the forefront of the next generation of data structures, there's a good chance that his work will be included in the java core (although that's not saying much considering).
Hmm... lemme think about that. Maybe because Java has decent threading support built into the language? Maybe because the platform is portable to any architecture? Maybe because the JVM can "optimize the hell" out of the running Java code far better than you could "optimize the hell" out of your C++ by hand?
"Java is Slow" is a mantra that is easily 5+ years out of date. Java surpassed C++ performance many years ago, and by such a wide margin that no one even bothers running benchmarks anymore. Anyone repeating the "Java is Slow" mantra is merely branding themselves ignorant.
Javascript + Nintendo DSi = DSiCade
Java has a well-defined memory model. C++ (and C) do not; behavior depends on the hardware it is run on.
700 threads in assembler? Why not use JAVA, actually optimize the hell out of the code, and get it down considerably. Or get a lot more done per thread.
Or... is this just a way to avoid having to get the really, really good coders who are more costly than the burn-bags?
I don't think architecture portability is a concern when you're writing for a 768-core supercomputer :)
Java surpassed C++ performance many years ago, and by such a wide margin that no one even bothers running benchmarks anymore.
Okay, I'll agree that well-written Java code is generally performance-competitive with compiled code, but this is a pretty sweeping assertion. Do you have any evidence for it -- or is it just a little too convenient that "no one even bothers" with benchmarks?
The correlation between ignorance of statistics and using "correlation is not causation" as an argument is close to 1.
Congrads Slashdot, you've managed to produce a story that is guaranteed to totally baffle the non-techie sector.
...
KeyWords:
concurrent data structures, hardware threads, java, large array, scalable parallel access, atomic update, words, finite-state machine, lock-free, data structures
davecb5620@gmail.com
"Because the code is written faster in Java, runs as fast as C code can (because the JIT does an equivalent job; plenty-o-examples upon request)"
Sorry , remind me what language the JIT compiler is written in. Java is it? No , thought not.
1. A common killer in parallelization is false sharing. That is, threads on two processors fight over a cache-line even though they are accessing independent variables. A cache-line is typically bigger than an individual variable. The approach of using adjacent elements of an array for parallelism sounds naive. One needs to pad the array.
2. Updating a shared variable, especially a non-scaler, in an inner loop is naive. One should reference local scalers in inner loops when parallelizing. Just once, should the thread update the shared variable. Don't reference non-scalers or shared variables in an inner loop. Don't lock in the inner loop, either, if you can avoid it.
If it is not an inner loop then the locking is probably not a big issue any way.
3. Java, really, Java?
"No one likes working in a hamster wheel, and your shop smells of cedar shavings from here." - TaleSpinner
Now *that* is what I call geek speak.
There is no way anything less than _really_ good coders would get something like this to work with any semblance of efficiency. If you still evaluate coders by which language they use, chances are you're not really that good a programmer.
sudo ergo sum
Umm, because Azul runs the Java in hardware. It *is* optimized by being in Java.
It's all machine language down at the bottom. So what's your point?
The "cue the foo posts in 3, 2, 1..." posts will commence with no subsequent foo posts in 3, 2, 1...
Actually I like being a COBOL consultant/programmer I get to work when I want and I get paid really big bucks. Lots of COBOL still out there in mission critical processes.
Undetectable Steganography? Yep, there's an app fo
It's not really "lock free". The algorithms in the slides still have WHILE loops wrapped around atomic compare-and-swap operations, so they are effectively spin locks, tying up the CPU while the other CPUs do something. However, the design is such that the WHILE loops shouldn't stall for too long.
This concept has two parts - a way of constructing bigger atomic operations from hardware-supported word-sized atomic operations, and a scheme for resizing arrays while they're in use. The latter is more important, especially in Java; stalls due to array resizing are a headache in real time systems with dynamic memory. It works about the way you'd expect; there are flags indicating the location (old or new) of each array element as the array is copied. Making all this work correctly is touchy.
Concurrent algorithms like this are incredibly hard to write, and you need formal methods to get them right. The author of the paper still hasn't figured out to code a FIFO under these rules.
Well, actually, it's 16 Vega2 chips (each of which is termed a "processor"), each chip has 48 cores, making for 768 total cores. 2 chips per board, and 8 boards in a system. All chips are fully meshed (no switch, fabric, or bus, just a whole bunch of direct multi-GHz wires), so it's a flat SMP UMA machine.
...).
The new Vega3 (announced last week) takes it to 54 cores per chip, and 864 cores in a system (16 x 54 = 864
700 threads in JAVA? Why not use C++,
To get the work done and working correctly before the hardware is obsolete.
sudo ergo sum
"# A Finite State Machine (FSM) built from the atomic update and logically replicated per array word. The FSM supports array resize and is used to control writes."
Clearly, the data structures have been touched by his noodly appendage.
If you can read this, I forgot to post anonymously.
Sure, Java manages memory for you, but it's generally much easier to incorporate a garbage collector into C than it is to write java without file I/O.
Badass Resumes
Azul hardware (which is in production with 768 cores), supporting 700+ hardware threads in Java
Hmmm... one core per Java thread?
That sounds about right for Java apps...
Just my
But above you talked about how JIT compilers sucked. So if we go by the usual logic of X Java program sucks -> Java sucks, then clearly the language that the JIT compiler is written in must by extension also suck, no?
This still has limited applicability. Making a single data structure useful across hundreds of CPUs is impressive, but many problems can be more easily solved by using multiple structures - pipelining it, or using divide and conquer, or any of many other approaches.
17.7 Non-atomic Treatment of double and long
Some implementations may find it convenient to divide a single write action on a 64-bit long or double value into two write actions on adjacent 32 bit values. For efficiency's sake, this behavior is implementation specific; Java virtual machines are free to perform writes to long and double values atomically or in two parts.
For the purposes of the Java programming language memory model, a single write to a non-volatile long or double value is treated as two separate writes: one to each 32-bit half. This can result in a situation where a thread sees the first 32 bits of a 64 bit value from one write, and the second 32 bits from another write. Writes and reads of volatile long and double values are always atomic. Writes to and reads of references are always atomic, regardless of whether they are implemented as 32 or 64 bit values.
VM implementors are encouraged to avoid splitting their 64-bit values where possible. Programmers are encouraged to declare shared 64-bit values as volatile or synchronize their programs correctly to avoid possible complications.
The author has developed a programming methodology class for parallel programming in Java. In this system, a single application can have 700+ separate threads running (user input, background tasks, dialog windows, scripts, automatic undo logging).
With such applications you will often have a array of variables that are accessible by all threads (eg. current processing modes of the application).
To preserve the integrity of the system, you need to only allow one thread to write to each variable at any time. If you have a single read/write lock for all the variables, you will end up with large number of threads queuing up in a suspended state waiting to read a variable, while one thread writes.
The author uses the Load-Link/Store Conditional pair of instructions to guarantee that the new value is written to all locations. Load-Link loads the value from memory. Store-Conditional only writes the value back if no other write requests have been performed on that location, otherwise it fails.
Check-And-Set only replaces the variable with a new value if the value of the variable matches a previously read old value.
Using these methods (having the writer check for any changes) eliminates the need for suspending threads when trying to read shared variables.
Vintage computer adverts: http://www.vintageadbrowser.com/computers-and-software-ads
He never said that Java had surpassed C in speed, he said that Java had surpassed C++. C++ library classes are not the same as C library classes, and many C++ libraries (especially the ones outside STL and Boost) are woefully under optimized. Java has many more optimized libraries "packaged in" with the language itself.
Second, neither the Doom or Unreal engines are multi-threaded. Java has threading support built into the language. To get the same with C you'd have to use POSIX threads (killing Windows compatibility) or the Windows threading API (killing POSIX compatibility). With Java, you don't have to make that choice.
We all know what to do, but we don't know how to get re-elected once we have done it
When you have a highly parallel system, it is counter-productive to try to make the workload sequential.
Nowhere in the article is it mentioned anywhere that they are running "700 hardware threads". Thousands of threads are typical of java applications even running on Pentium IIIs. Every J2EE Application server spawns a new thread for every request. It's part of the specification. The real issue with Java is the hard thread limit in most JVMs where even calling -Xss will not override the limit. These limits are both asinine and arbitrary. Linux can very easily handle the instantiation of millions of pthreads on a single core host, and we all have multi-core machines these days. The JVM ought to scale to millions of threads, otherwise if a JVM can only support 20k concurrent threads, there really isn't any reason to ever pay more than a few hundred dollars for a web server since you quickly reach the maximum thread count while 99% of your opteron system is pretty much sitting there doing nothing.
Furthermore, the need to synchronize a collection is an indication of poor design (i.e. lack of encapsulation) that is better solved by writing better code that doesn't use disgusting global data structures, but if you really wanted to use a shared collection, all you would have to do is create an implementation that makes each object in the data structure lockable individually, like a linked list where any index could be locked independent of the list itself, and new capacity could be created and then added in bulk. But in the end, updating a collection is a simple constant time operation (just update the reference to point to a new location), so you should never have performance problems even when locking an entire collection to do the update. If you are having performance problems with that, then chances are, it is the way that you are interacting with the collection.
Anyway, here's to hoping that people can learn basic programming concepts so that the world can move on to solving real problems.
I used to think this too until I saw the video by the article's author. By lock free we mean that if the thread that has the "lock" were to die, it would not stall out the entire program. With CAS updates, a crashing thread would simply die and cause no ill effects to the data structure. With Mutex style locks, if the locking thread crashes (or otherwise forgets to unlock the mutex) then the entire program grinds to a halt as other threads start waiting on the lock. The maximum time a CAS "lock" can exists is 1 CPU cycle.
Man is the lowest-cost, 150-pound, nonlinear, all-purpose computer system which can be mass-produced by unskilled labor.
Take a look at the algorithms in the presentation. I've done a fair amount of lock-free programming, but all of it was in C. His algorithms look like standard lock-free practices, but since I'm not familiar with what correct lock-free Java code looks like, I can't say with confidence.
I will, however, say that I would be surprised if Cliff Click made such the obvious error you assume he is making. I saw him talk at ISMM 2006, and I trust him more than random people on slashdot.
Java is perfectly fast for real world applications, and I'd agree that the "Java is Slow" idea is outdated.
But it's not conclusively faster than C++, at least not in a general sense. In terms of a small task involving lots of simple operations, you'll still often see a significant speed increase using C++. This is a good example. Now I'm sure there's more optimizations available on both sides - and plenty of stuff to tweak - but C++ is going to come out ahead by a significant margin on a lot of these tasks.
A good example where the participants on both sides have some motivation is on TopCoder (where I spend a fair bit of time). Performance isn't usually the driving factor in language choice there - but sometimes it is, and when it is the answer is pretty much always C++ (unless it's a comparison between Java BigInteger and a naive implementation of the same in C++).
Reasonably often you'll see people write an initial solution in Java, find it runs a bit too slow, and quickly port it to C++ (or pre-emptively switch to C++ if they think they'll be near the time limit). It's not uncommon to see a factor of two difference in performance.
To be clear - these are not usually "real world" tasks. As more memory and objects come into play, Java is going to do better and better. But these kinds of tasks still exist - there's still plenty of places where C++ is going to be the choice because of performance.
In any case, your contention that Java is so much faster that nobody does benchmarks anymore is unsupported and wrong.
Let's not stir that bag of worms...
He's built two working data structures and is working on a third (had to read the slides to figure that one out).
Yes, Java didn't surpass, but was competitive with C++ many years ago - at least as far as CPU goes. In fact, if you use gcj, you'll find that Java performance is *very* similar to C++ :-). For the IBM JVM, the turning point was JDK 1.1.6. I think having each thread allocate blocks of memory to dish out without lock contention was a big part of it. One interesting benchmark was this.
Now, before you C/C++ or Java fanboys get too excited, the absolute hands down fastest language on most of the benchmarks was LISP (I think it was Common LISP). I don't use LISP because I hate the syntax (and LISP fanboys regard it as a requirement of club membership that you like it). But the performance is quite impressive (with GC too), and that's what I would look into if I needed top performance from a high level language. Eat your heart out C++.
I use Java quite a bit, and the biggest drawback performance wise is the amount of memory chewed up by the GC schemes and JIT. It is otherwise quite fast. I often turn off JIT to save memory (at the expense of CPU), and I would like to see options to use a GC algorithm that minimizes memory consumption (at the expense of CPU).
Thanks for the awesome advice. x86 assembler is clearly the obvious choice for anyone writing a web or desktop application.
I hereby appoint you official summary explainer!
Thanks
AT&ROFLMAO
Well the AVR32 architecture does support some Java byte codes.
:)
Mind you the manual does specifically state that you shouldn't use them inside interrupts.
I just pictured 700+ worker(-threads) in front of a huge panel with 700+ switches. I think that is where assembly(-line) coding came from.
Which is great and all, but what we usually need is more of a summary executioner.
Post may contain irony: discontinue use if experiencing mood swings, nausea or elevated blood pressure.
In the problems that TFA addresses, I'd wager that most of the time is spent in dissemination barriers of some sort, since invariably the problems in parallel computing move into issues within the problem domain (which is ideally what we want, after all).
As for a JIT being inefficient compared to a static optimizing compiler, it depends so much on the code in question and on the platform, as to not be something you can make blanket statements about.
Let's hear from some HPC researchers on this. Get some real numbers.
-fb Everything not expressly forbidden is now mandatory.
Well... if I remember what I learned from OS and hardware classes right. LL/SC and CAS operations do involve locks at the hardware level. These operations may need no OS system call, may use no explicit semaphore or lock, but the memory bus has to be locked briefly -- especially to guarantee all CPUs seeing the same updated value, it has to do a write-through and cannot just update the values in cache local to the CPU. And when you have large number of CPU cores running, the memory bus becomes the bottleneck by itself.
So I fail to see anything radically new in this project. It is not lock-free at all. It sounds more like bogus marketing pitch to me.
Can someone correct or explain to me?
They develop Java hardware for internet applications . Presumably this is for commercial organisations where it is more important to get a functional application designed and assembled than to design/test and implement a completely optimised C++ application.
Vintage computer adverts: http://www.vintageadbrowser.com/computers-and-software-ads
As much as I love assembler, it's an offer vs demand thing. Very few people are actually proficient at assembler coding, but a crapload of morons can write a thousand lines of useless Java code a week, and they're willing to work for peanuts. Assembler guys want big bucks, mostly because their rarity gives them that power, along with the obscurity of the art.
Let's face it: there are some low-level things you just can't do in any language, and asm coders know it! If it's only a speed issue, it's usually cheaper to throw more hardware at the problem and let the cheap idiotic factory coders chew on it.
-Billco, Fnarg.com
They are really non-blocking, and use a standard Java API - the java.util.concurrent.atomic package. The description of the package indicates it was intended as the low level basis for non-blocking data structures. While most JVMs are written largely in C, the Java code gets compiled to machine language. Standard packages do not have to be implemented via JNI, and can be implemented directly by the JVM - just like GNU C implements many standard C library functions directly in the compiler for performance. In fact, java.util.concurrent.atomic would be a poor choice for implementing via JNI because the transition between C and Java code that happens on every JNI call would defeat the high performance purpose of the package.
Since you're apparently reading this - shoot me an email. I'd like to discuss if this could work with Jython.
I'm thinking using a single Honkin' Big Iron instead of a farm for a massive-use service.
TransactionKit is another lockless highly concurrent data structure, specifically a hash table.
But a FSM-controlled data access for multi-threading is a bit different. The closest I've seen is the implementation of dual-port RAM which uses hardware state machines to control access to the underlying shared RAM.
Oh, I've been doing embedded for over 20 years too.
Engineering is the art of compromise.
700 threads in JAVA? Why not use Brainfuck, actually optimize the hell out of...no wait, fs my head hurts now:(
I'm a rabbit startled by the headlights of life
Someone posted the video and that was great. In particular I really like the use of a finite state machine as a proof of correctness. That might be a novel approach in this day and age when everyone is in love with UML. It makes you wonder if many of these things aren't made too complex by adding too much cognitive over-head. To hear Dr. Cliff Click talk it seems so trivial in retrospect. I suppose this is how you know his solution is elegant... I seriously doubt I'd have thought of it myself but when you see something elegant that seems natural afterward it's probably right.
The other thing is that his algorithm shows a remarkable departure from traditional concurrent programming (as I learned it a decade ago) and he's not getting bogged down with locking and synchronize... instead he has a very simple "think about it" approach that uses the state machine as a thinking aide. Whom ever posted the video... thank you that was very enlightening. Perhaps many of these concurrency problems just need some creativity after all?
[signature]
Software is for noobs. Consider Verilog.
Your link says: "Unfortunately, there's also a third conclusion. It seems that it's much, much easier to create a well performing program in Java. So, please consider it for a moment before you start recoding your Java program in C++ just to make it faster..."
In any case, the author of that test failed. The test includes start-up times in the results. Java is always going to lose micro-benchmarks where start-up time is included. Why? Because the JVM load gets included in the benchmarks. As anyone who knows Java well can tell you, Java's startup time is extremely costly. Once the JVM is running, however, it produces much better performance. The end result is that the startup cost will eclipse the actual benchmark being run.
I'm willing to bet you'll have a hard time finding a modern benchmark for Java that doesn't make that (simple!) mistake.
However, I will admit that I was overextending my reach by suggesting that no one runs benchmarks anymore because of the strong performance of Java. The reality is (as one might expect) much more complex. It's not that Java performed poorly in benchmarks. Quite the contrary. By 2004, Java was cleaning up in benchmarks. The problem is that micro-benchmarking sucks. All you end up getting is the two sides fighting over who can produce the most optimized benchmark possible. Which invariably ends up defeating the purpose of benchmarking for "real-world" code.
The long and short of it is that Java was proven to be more than fast enough, with the average case easily keeping pace or beating C++ code. Thus the statement by the author of the article you linked to:
"Unfortunately, there's also a third conclusion. It seems that it's much, much easier to create a well performing program in Java. So, please consider it for a moment before you start recoding your Java program in C++ just to make it faster..."
Javascript + Nintendo DSi = DSiCade
If the problem is inherently slow, then the speed of the language really isn't the issue. Most of the time will be spent waiting on network I/O or similar. In this case it's better to have more understandable code and a more verbose network protocol (e.g., using XML) than it is to optimise such a process away.
For the vast number of places that Java is actually programmed, it is a very good choice of language because (a) it's well known, (b) it has loads of third party libraries, and (c) it performs good enough, threading is easy so you can just add cores to your solution, and so on.
These are probably the same people that think that Java + Struts/Spring/Hibernate is hard and slow, and then try and reinvent the wheel in PHP.
Because the cost of developing your code in ASM would be a gigantic leap in terms of time and provide little in terms of gain over the output of a good compiler. It would also destroy any potential for reuseability on other platforms.
The parent on the other hand I can agree with, Java development is not much faster then C++ provided you are working on more esoteric things and can't take advantage of the huge library selection. The syntax is formal patterns are mostly the same after all. Developing a massively parallel application targert at multi-hundred core boxen most likely implies you are doing something rather esoteric. If you are going to make the investment in massive and specialized hardware it would seem to me you would also want to make the 'slight' extra investment and write a C++ or C application rather then a Java one. You can with a little thought up front produce fairly hardware agnostic C and C++ so you don't really lose the portability. Infact given we are talking about fairly specialed hardware and software platforms here there may not exist a usuable JVM for the next platform you want to move onto, so C or C++ might be more portable.
Repeal the 17th Amendment TODAY! Also Please Read http://www.gnu.org/philosophy/right-to-read.html
it is the platform (i.e. JRE). Slow. As molassas. But then again, so is managed C++ on the CLR.
So it goes, the circular argument....
I am very small, utmostly microscopic.
disclaimer:I am C/C++ fanboi
Java is not faster then C++ and it never will be. You can't fundamentally add the overhead of a byte code interpreter and somehome come out ahead. What Java does and does very well is save programers from themselves.
Like most programers I am not God's gift to software development. Chances are pretty good that as any given software project I am working on becomes larger and starts to involve more objects, and or data structures the memory management in Java is going to be better then that I would do myself. The garbage collector in Java is very good. It was implemented by very good coders who had a very specific interest that they could focus on. Whatever application I am doing has some other focus which means that managing memory is simply a required part of the task not the aim of it. Its a safe bet that my data managment is not going to compete with what is in Java. Now for small projects its a different ball of wax.
Repeal the 17th Amendment TODAY! Also Please Read http://www.gnu.org/philosophy/right-to-read.html
While I do love C++ (C is for OS programmers, which I am not) the truth is that JIT compilers perform optimizations that native compilers don't. They can inline things based on dynamic usage, they can inline library functions, they can even recompile based on the hardware the code is running on (similar to compiling a custom kernel in linux, but on the fly) . When all of this is working VM based languages can really fly.
Some of these ideas will eventually make it to native C++ compilers. However, I can't see all of them making the transition since they depend so heavily on having an intermediate form of the code to work with.
So, yes, bytecode can be faster than native code in certain situations. I think there's still a lot of work to be done with these compilers. "Certain situations" might well become "nearly all situations" in the future.
The test includes start-up times in the results.
This may be a significant factor for some of his smaller tests, but I don't think it jeopardizes the overall conclusion. For example, the Ackerman test was 15s vs. 60s. There isn't going to be more than a second of startup, and most of the tests are showing differences on the order of many seconds.
In terms of "is it harder to write fast code in C++", I guess it depends on what you're good at. Looking at the changes he did to the C++ code, none of it is esoteric - but I'm also more interested in this kind of thing than most of the programmers I know. I think it's fair to say many coders would produce faster code for these functions in Java than C++.
All in all, it's a subject that probably gets more attention than it deserves. Like you say, Java is plenty fast. Whenever I see performance problems at work, I never think "Ooh, let's rewrite this in a lower-level language" (and very seldom would that help). I think, let's look at the SQL, look at the bandwidth, look for other resource conflicts, or change overall approach.
Let's not stir that bag of worms...
Java doesn't necessarily involve a byte-code interpreter. JVMs have supplied Just In Time compilation for years now.
That's not a panacea though: optimization is generally a difficult task, and good optimization can be quite difficult indeed -- many (perhaps most) NP-complete problems are basically ones of optimization. While optimizing code isn't necessarily identical to a traveling salesman problem (etc.), there is quite a bit in common.
The result of that is that the really difficult optimizations are harder to justify in a JIT compiler. In a traditional compiled language, you compile a small number of times, and run many times. In a JIT environment, you compile far more often, so you can't amortize that cost over nearly as many executions.
I'm not convinced of this either -- Java adds garbage collection, which many people think will save the programmers from themselves. My experience indicates rather the opposite -- garbage collection makes very little difference to memory management, and lack of deterministic finalization makes most other resources considerably more difficult to manage.
There is no one garbage collector in Java -- there's a garbage collector in each individual JVM. Some of them are better than others, and some are optimized for different loads than others. Languages that use manual memory management are similar: each implementation has its own, with its own characteristics.
For that matter, quite a few people use garbage collectors with C and C++. These garbage collectors are generally implemented by extremely good coders as well. C and C++ place a few obstacles in their way, so it's a bit more difficult to implement them, but they work reasonably well nonetheless.
In the end, however, I think the effect of garbage collection on speed of either execution or development seems to be quite exaggerated. In a few circumstances, it's really helpful. In others it's really harmful. Most of the time, it makes very little difference at all.
The universe is a figment of its own imagination.
More accurately, Java is usually more than fast enough, even though it's nearly never as fast as equivalent C++. When you get down to it, performance rarely matters much.
The universe is a figment of its own imagination.
What's absurd about one bit of native binary code outperforming a different bit of native binary code? o_O
I mod down anyone who says "I will be modded down for this", regardless of the rest of their comment
Except that the whole reason you'd use one of these, instead of a much cheaper cluster of commodity hardware, is because you want to use shared memory and threads. There are problems which scale much better to shared memory than to shared-nothing -- or so I'm told.
Oh, and Erlang is wannabe-functional. Go play with Haskell if you want a purely-functional language. No side effects means, among other things, the ability to have the parallelism done for you, instead of having to explicitly spawn a thread -- or an Erlang "process".
Me, I'm working on a cute wrapper for Ruby objects to turn them into Erlang-style threads.
Don't thank God, thank a doctor!
Because as the article says, Java has a well defined and correctly implemented memory model that provides certain essential guarentees about ordering and memory consistency when dealing with high levels of concurrency. C++ does not (in its current form) have any well specified memory model, making his techniques impractical, if not impossible, since the behaviour is unpredictable. To acheive concurrent data structures in C++, the only way to do it safely, correctly and in a portable way, is to use locks. For this reason, you can expect to get much better performance in highly concurrent environments with Java with than you would get with C++.
The next version of C++ in development, is trying to provide such a memory model, based on Javas.
> Your turn.
:)
Catamorphisms. Linear Logic.
Back to you
Done with slashdot, done with nerds, getting a life.
So your argument is that with C/C++ you can make something almost as portable, almost as re-usable, almost as fast to write, almost as easy to debug, using a library selection that's almost as complete as Java. And in return you might gain a tiny bit of speed increase?
And you're also postulating that there's more likely to be a fully standards-compliant C++ compiler with a standard thread interface on all those esoteric machines of which you speak than a basic JVM?
I understand it's cool to hate Java on Slashdot, but sometimes I think the Java bashers are trying a little too hard.
E pluribus unum
This thread discusses the merits of the STM features of Clojure, a JVM language. It's another way to do lock-free concurrent programming on the JVM, using appropriate data structures.
Researchers don't work at the fringes of what can be done "more easily". They work at the fringes of what is currently possible.
Think about multi-tasking for a moment. If your problem is inherently sequential (e.g. everything is effectively sequentialised by a shared resource that can't be split, such as a piece of hardware), then you can use a single-process event loop. If your problem is inherently parallel (e.g. a web server), then you can use multiple forked processes. In otherwords: If your problem is easy, use an easy solution.
But not every job is easy. That's why we have multi-threading.
Similarly, these new data structures are designed to solve difficult problems.
sub f{($f)=@_;print"$f(q{$f});";}f(q{sub f{($f)=@_;print"$f(q{$f});";}f});
This is how we've been teaching computer science to share memory since there was more then one thread. Anyone over 40 will immediately recognize this as just "how we do that". To all you younger viewers, welcome to multi-core/SMP circa 1980.
And to all you industry people, if you'd stop firing everyone when they turn 30, you'd know this too!
- Adam L. Beberg - The Cosm Project - http://www.mithral.com/
From what I seen on Topcoder, C++ is preferred to Java mostly because it allows more compact coding using preprocessor. Generally I never seen any example that the same algorithm would run in 2 sec in C++, but more that 2 sec and so failed in Java. Also notice that all Topcoder application is written in Java.
I don't necessarily take issue with what you've said (I've got you on my friend list, so I'm fairly sure that your one of the professionals on this site whose insight I love to read... I'm a software development major in college, so I usually add programmers to my friends list when I genuinely value their insights...), but I would like to point out that I've seen another approach to your first point about locking busses. The Linux kernel, IIRC, does a sideways and backwards cache flush to RAM before masking IRQs on an SMP system. I think it defers top half of interrupts to another CPU and doesn't queue the bottom halves. I might be mistaken on that, though. It then 'takes over' the CPU for the process/thread, and when it's done, it flushes all the caches once again.
But, as you said, the lock doesn't require a bus lock. Please correct me if I'm wrong on this, it's been a few months since I've read that piece of code and I'm a little hazy on the exact details.
If I mod you up, it doesn't necessarily mean I agree with what you've said, sorry.
When performance doesn't matter much I'd use perl instead of Java, or some other higher level language (e.g. Python).
:).
;).
Of course when your boss/customer requires Java, use Java
I'm mixed on Lisp- Lisp is kind of high level and kind of not... I guess I'm just too lazy - perl has CPAN = lots of wheels I don't have to reinvent - and document
We outsourced that to China.
They said they'd provide nonblocking executions in a scalable manner.
Well, nothing... but based on the GP's usage of the phrase "JIT bytecode", my best guess is that he's talking about Python (compiles source code to bytecode "JIT") as opposed to Java (compiles bytecode to machine code JIT).
If speed if your concern, why would you switch from Java to C++ instead of just switching from JRE to gcj native? Is there really a significant difference between gcj and g++ in terms of speed? I guess Java has bounds checks which are probably not completely optimized out, but they could be disabled with --no-bounds-check.
Centralization breaks the internet.
Call me old fashioned, but ummmmm, you malloc() it , you free() it.
I mean when did this whole notion of malloc() it and forget it come to pass? Did Ron popeil suddenly start writing programming languages or something? I don't care how complex your code is, at some point that bit of memory is no longer required and at that point it is your job as the programmer, to clean up after yourself and free() it, no?.
Hey KID! Yeah you, get the fuck off my lawn!
Java GC sucks in general. I use quite a number of different JVM's and the tuning advice I see most often and have experienced is don't allow any given JVM to go above ~1.5GB of ram or GC performance will bring down overall system performance. That's just stupid on modern machines with up to hundreds of GB of ram. Sure there are frontends that allow you to spawn additional JVM's automatically, but that just means there's more processes and more overhead.
There are 4 boxes to use in the defense of liberty: soap, ballot, jury, ammo. Use in that order. Starting now.
I think the deal is that, ultimately, lower-level languages (assembly is lower than C, which is lower than C++, which is lower than Java) allow you to gain better performance than you could achieve with higher-level languages.
Whether you will actually achieve the highest possible performance depends on whether you actually write the most efficient code possible. This, in turn, depends on your skills and the time you have to complete the project.
Thus, what you will see in practice is that there is a lot of variance in the performance of programs written in lower-level languages, and less variance in the performance of higher-level languages. Libraries also have a huge influence here: the more code you use from a library, the faster you will complete the project and the less variance there will be between your program that uses that library and someone else's program that uses that library.
The final result will probably be that the fastest programs are in the lowest level languages (provided these programs exist at all), but, largely, the speed scales will overlap. It may even be that the slowest programs in a lower-level language are slower than the slowest programs in a higher-level language.
Thus, it is not a priory obvious that lower-level programming languages will yield faster programs than higher-level ones.
For another data point, have a look at OCaml. With garbage collection, polymorphism, classes and objects, and type inference, it's definitely a high-level language. In my experience, it's much nicer to program in than Java, and the implementation offers run-time performance that is about on par with Java and often a lot better.
Please correct me if I got my facts wrong.
Not entirely sure what that has to do with my post, but thanks, that's interesting.
I'm also not entirely sure I like transactions yet. Haven't thought hard enough about it, yet.
Don't thank God, thank a doctor!
Because coding a bad, poorly parallelizable algorithm in ASM vs C will give you at best a 2x speedup.
And coding a good, hyper parallelizable algorithm in Java vs C will give you at worst a 1/2x speed down, and at the same time an nx speed up, where n=768.
And I'm not even talking about the mess ASM would be.
Usually scalable algorithm are slower when the CPU count is low so the question is: how many CPU are needed so that the scalable algorithm is as good as the non scalable one?
Strangely this isn't talked about in this 'lightweight' article..
Amb. Calculus of constructions. Higher-order barbed bisimulation. Stochastic processes. :)
And you're cheating with your signature
See also the hyperoperators of Perl 6:
http://www.google.co.uk/search?q=perl6+OR+perl.6+hyperoperators
Also a lot of "fast" C programs out there also have big asm blocks and/or massive amounts of align hints. That kinda stops it begin C.
IMHO there are just a few areas where a asm/C block will trash any pure java implementation. Thats symmetric crypto and video codecs. Its easy to see why too. Cryto algos are often designed from the ground up with x86 asm in mind. Where MMX etc was introduced really for DCT type calculations.
If information wants to be free, why does my internet connection cost so much?
Though this is one of the things that they should look into fixing in newer versions of Java. They really need to go ahead and make a version that is extensively similar to, but not necessarily backwards-compatible with, previous version, that is more internally consistent and less verbose. I've been coding Java for almost a decade, and I still have to stop and think about whether I need to call size or length.
Thomas Galvin
I wrap my enigma in a factory class
I have discovered a truly remarkable sig which this post is too small to contain.
You're correct in that people don't generally choose C++ based on performance. But it does happen that non-C++ coders will switch for certain problems.
As an example, As here is Kawigi (a fairly high level competitor who usually uses Java), switching to C++ so he can brute-force a problem instead of using DP.
Notwithstanding that, all TopCoder problems (well, all correct ones) have a Java solution that runs in under 1 second - as that's the requirement on the reference solution. Where you'll see switches to C++ is to make other approaches feasible.
Let's not stir that bag of worms...
And, going back to my original point, neither cryptographic algorithms nor video codecs are multithreaded. In fact, video and audio encoding are some of the few things that really benefit from massively long pipelines and high clock speeds (which is why the old P4s used to do that sort of thing well).
We all know what to do, but we don't know how to get re-elected once we have done it
Well, if you're already abstracting away that much, why not go to Java where you don't have to worry about your abstraction being under-optimized?
We all know what to do, but we don't know how to get re-elected once we have done it
In Computer Science terms, atomic operations are ones which prevent the 'he who writes last - wins' syndrome.
In multiprocessor architectures the use of resource locking normally does the job, although one of the drawbacks is forcing other threads of execution to wait until the lock is released. There are non-locking and wait-free methods that use low level atomic operations (like 'compare and save') and generally use data structures that support these methods (stacks, queues, sets and hashes).
Lodragan Draoidh
The more you explain it, the more I don't understand it. - Mark Twain
Anything like this (Scalable Nonblocking Data Structures) but on C/C++?
Wouldn't a more objective comparison show Java's throughput over time while running these tests? The way he munges the source bothers me as well. Instead of subjectively modifying the code so it seems 'fair', shouldn't the tests include little or no calls to standard libraries or other classes? Or, if you are going to compare those things, do a baseline as I suggest, then call the following tests what they are.. a Vector vs. HashMap or whatever comparison. Reasonably often you'll see people write an initial solution in Java, find it runs a bit too slow, and quickly port it to C++ (or pre-emptively switch to C++ if they think they'll be near the time limit). It's not uncommon to see a factor of two difference in performance. Where do you see this? The 2x gains and 'quick' Java->C++ ports that is, not the preemptive bit, I could care less about all this subjective garbage. In any case, your contention that Java is so much faster that nobody does benchmarks anymore is unsupported and wrong. That benchmark you provided is crap.
Look, I'm just picking on you because it feels like you're comparing two cars by the HP number on the sticker instead of looking at a full dyno chart
To expand on your comment, I would say there are certain tasks that are suitable for all the languages listed (and then some):
Assembly - embedded systems/drivers for a given platform.
C - larger systems programming tasks that need to be portable -- too big to be effectively built in Assembly without going crazy, too small for C++; you can embed Assembly instructions in C as needed - so you can have your cake and eat it too.
C++ - for complex systems requiring near-real-time response (e.g. multiplayer video game).
Ada - for complex systems requiring real-time control (e.g. avionics) without error.
Java - for complex systems not requiring real-time control or response (e.g. GUI Office Suite that interfaces to user via http).
Python - for simple or complex systems not requiring real-time control - but where speed of deployment/refactoring is more important than processing speed (e.g. embedded control language, or specialized control/reporting interface tied to a changing back-end system).
It is thus irrelevant to talk about 'java is faster than C++' or any similar argument, without including a complete evaluation of the factors involved in a given project. The factors would include, the time required to complete the project, as well as performance factors.
We can certainly agree that building a GUI http interface using Assembly would not be optimal, given the ease of using Java to do the same thing. Of course, there may be an instance when it would be more desirable (perhaps building it in an embedded system with severe limitations on memory or performance).
As a developer, you should be able to reach into your bag and pull out whatever tool is best suited for a given job. One-trick ponies end up in the glue factory.
Religious wars are counter productive. We should frame the discussion to examine the practicalities of a given set of projects.
Lodragan Draoidh
The more you explain it, the more I don't understand it. - Mark Twain
I'm pretty sure a large majority of the users for this technology are "FINANCIAL" customers, where latency matters. Stock trading companies come to mind - requires very high performance / w low latency. Yes, alot of them write their software in Java (not C++)
We use these JVM options on a box with 16GB, and we could even increase the Xmx=12G to more and it would be fine, but we wanted to leave some room for disk cache.
JAVA_OPTS="-server -Xms3000m -Xmx12000m -Xss256k -XX:ThreadStackSize=256 -XX:-HeapDumpOnOutOfMemoryError -XX:-PrintGCDetails -XX:MaxPermSize=256m -XX:-PrintGCTimeStamps -Xloggc:/path-to-log-dir/gc.log -Dsun.net.inetaddr.ttl=10 -Dsun.net.inetaddr.negative.ttl=0 -Dsun.rmi.dgc.client.gcInterval=1800000 -Dsun.rmi.dgc.server.gcInterval=1800000"
Use the GC log option to watch it in action. You can safely ignore the DNS cache stuff, but I like to add it to every JVM to fix that major annoyance.
This is for Sun JDK 1.6 btw. We used different settings for JRockit.
Where do you see this?
I posted one example, and it would easy for you to find others. For myself, I don't feel any particular obligation to further establish this.
As to the guy's benchmarks, they seem fairly reasonable to me. I don't think it's unreasonable to include things like vectors and hashmap implementations when talking about the speed of a language - and the benchmarks this guy was countering did the same thing.
You're also confused on my motivation, I think.
I don't hate Java. I was arguing against the idea that it's so much faster than C++ that nobody measures it anymore. Even if Java would outpace C++ if it was let to run for longer or something, we'd still be left with the conclusion that there are some tasks C++ is faster for (which is all I was trying to establish).
Do you want to disagree with that?
Let's not stir that bag of worms...
And in the meantime, clever guys who decided not to spoil their lives with half-baked programming languages are doing things in a much more beautiful way...
Ezekiel 23:20
IF you malloc, SET it free!"
Huh. The most straightforward answer, and the one that seemed least likely to me....
Media that can be recorded and distributed can be recorded and distributed.
-kfg
"When I find myself in times of trouble, Dennis Richie comes to me, speaking words of wisdom, code in C, C, C, Ceeeeeee".
With apologies to so many.....
Hey KID! Yeah you, get the fuck off my lawn!
Has it been done?
Do we have anything besides junk micro-benchmarks? Is that just a phrase that's been repeated for years on the internet?
I'm not kidding with you. When I hear stuff like that, I can't help but ask for details. I don't hate Java. Um... good? It's pretty silly to get all emotional over programming languages. I was arguing against the idea that it's so much faster than C++ that nobody measures it anymore. Which dumbass said that? Are you sure the idea wasn't that it's often fast enough where it's not worth the effort to port to C++ just to find out?
But, if someone has, I'd be interested to know. Even if Java would outpace C++ if it was let to run for longer or something, we'd still be left with the conclusion that there are some tasks C++ is faster for (which is all I was trying to establish). Well, you're right, there are tasks that C++ can perform better than Java. Why didn't you just say that?
In the end, both can produce well optimized code, but I haven't read anything suggesting that the structure of either language enables fundamentally better optimizations than the other.
Are you sure the idea wasn't that it's often fast enough where it's not worth the effort to port to C++ just to find out?
Here's the part of the original post I was replying to:
Java surpassed C++ performance many years ago, and by such a wide margin that no one even bothers running benchmarks anymore
I suppose one could read that in a number of lights, but it seemed a bit off to me.
Let's not stir that bag of worms...
Do you have definite proof of that categorical statement or are you talking out of your ass?
In general, I have found that most benchmarks in which Java surpasses C++ in speed were done by people who have either poor understanding of C++ (using sub-optimal constructs) or poor familiarity with the compiler (using sub-optimal optimization options).
Here's what I found:
On Athlon, every individual test ended with C++ performing better than Java. Overall, C++ was three times faster than Java.
To summarize:
1. That when benchmarking an algorithm in a programming language, you have to use the most efficient implementation for the language you are testing.
2. That it does not matter that language X is slower than language Y as long as it is fast enough for the task at hand.
3. That AKAImBatman was talking out of his ass.
Best regards,
Alex