|
I've read your explanation, but I'm not convinced they support your assumptions (which, barring any benchmarks that make them factual, is what I consider them to be). I'm aware of the dynamic dispatch overhead of Objective-C, but first of all it's my understanding that Apple's Objective-C runtime & compiler perform all kinds of smart tricks to reduce the overhead to a minimum (caching selector lookups and such), and second, because Objective-C does not require you to use dynamic dispatch if performance is a concern. No one is preventing you from doing plain-old C-style functions for performance criticial sections. I also don't buy the 'ARC is slower than GC' argument. ARC reference counting on 64 bit iOS, as implemented using tagged pointers, has almost zero overhead for typical workloads. Only if you would write some kind of computational kernel that operates on NSValue or whatever (which is a dumb idea in any scenario, about as dumb as writing such a thing in JavaScript) you would ever even see the difference between not having any memory management at all. Just like your other performance claims: without data, there is nothing that backs up your statement that ARC is slower than GC for typical workloads. Hans Bohm is not the most objective source for such benchmarks by the way. Apart from that you seem to spend an awful lot of effort explaining the things that would make Objective-C slower than JIT'ed JavaScript, while completely disregarding the overhead all this JIT'ting, dynamic typing, etc has, and the fact that in JavaScript you basically have no way to optimize your code for cache friendliness or whatnot. You may be a compiler developer, but based on your comments I'm highly doubtful you are aware of how much optimization already went into Apple's compilers, which greatly reduce the overhead of dynamic dispatch and ARC. |
That's just writing C, not Objective-C. But if we're going to go there, then neither does JavaScript. You can even use a C compiler if you like (Web Assembly/asm.js).
> ARC reference counting on 64 bit iOS, as implemented using tagged pointers, has almost zero overhead for typical workloads.
No, it doesn't. I can guarantee it. The throughput is small in relative terms, I'm sure, but the throughput would be smaller if Objective-C used a good generational tracing GC.
(This is not to say Apple is wrong to use reference counting. Latency matters too.)
> Just like your other performance claims: without data, there is nothing that backs up your statement that ARC is slower than GC for typical workloads. Hans Boehm is not the most objective source for such benchmarks by the way.
There's not much I can say if you're determined to discount real numbers solely because Hans Boehm provided them. But here you go ("ARC" is "thread safe"): http://www.hboehm.info/gc/nonmoving/html/slide_11.html
Anyway, just to name one of the most famous of dozens of academic papers, here's "Down for the Count" backing up these claims: https://users.cecs.anu.edu.au/~steveb/downloads/pdf/rc-ismm-... Figure 9: "Our optimized reference counting very closely matches mark-sweep, while standard reference counting performs 30% worse." (Apple's reference counting does none of the optimizations in "Down for the Count".)
Here's the Ulterior Reference Counting paper, showing in table 3 that reference counting loses to mark and sweep in total time: http://www.cs.utexas.edu/users/mckinley/papers/urc-oopsla-20...
memorymanagement.org (an excellent resource for this stuff, by the way) says "Reference counting is often used because it can be implemented without any support from the language or compiler...However, it would normally be more efficient to use a tracing garbage collector instead." http://www.memorymanagement.org/glossary/r.html#term-referen...
This has been measured again and again and reference counting always loses in throughput.
> You may be a compiler developer, but based on your comments I'm highly doubtful you are aware of how much optimization already went into Apple's compilers, which greatly reduce the overhead of dynamic dispatch and ARC.
I've worked with Apple's compiler technology (clang and LLVM) for years. The method caching in Objective-C is implemented with a hash table lookup. It's like 10 instructions [1] compared to 1 or 2 in C++, which is a 3x-4x difference right there. But the real problem isn't the method caching: it's the lack of devirtualization and inlining, which allows all sorts of other optimizations to kick in.
Apple did things differently in Swift for a reason, you know.
[1]: http://sealiesoftware.com/msg/x86-mavericks.html