> But reachability is not liveness and so a GC is an incomplete solution too.
Not sure what you mean by that. If you mean that objects are usually not immediately released but occupy memory for a time, yeah, that's known, but the overhead from that can be bounded; ownership models lead to excess copying and thus memory overhead, too, as they don't handle shared and multiple ownership well. If you mean that objects may not actually be in use any longer even though they are reachable, manual memory management doesn't fix that, either. Also, languages without a GC will almost invariably end up building an ad-hoc reference counting scheme for whenever an ownership-based approach is not expressive enough, getting you a subpar GC anyway. It happened with C++, D with `@nogc`, and with Rust. > If you encourage programmers not to think about memory management since the > GC handles it, what do you think happens? I didn't say that you should encourage people not to think about memory management. I said that a GC allows you to encapsulate or abstract over memory management concerns. > Add multi-threading and the complexity of the runtime becomes scary. Yes, but the underlying problems don't go away just because you jettison the GC; a GC for multi-threaded programs with a shared heap solves hard problems (which is why it is hard to write), and those problems don't become easier if you don't have the GC. If you have shared memory concurrency, then object lifetimes become increasingly hard to reason about for any non-trivial concurrency logic over shared objects. (That, or you create serialization bottlenecks.) I am personally increasingly leaning towards the Erlang/Dart model, with shared memory only being used as an optimization fallback (zero-copy message passing, arrays/matrices over scalars or other pointer-free data). > Cliff Click probably forgot more about GCs than I'll ever know and yet he > thinks about going for Rust-style MM in his language experiments: That's his choice. Rust's model has big problems when it comes to structural sharing or divergent lifetimes. Linear and affine typing systems run into big problems with shared or multiple ownership. For example, the Rust implementations of persistent data structures that I know of all use `Arc<T>` (atomic reference counting), which is pretty horrible for performance.
