Hacker Newsnew | past | comments | ask | show | jobs | submitlogin

It’s not really copy-on-write though. That implies greater systemic performance losses than what Clojure provides, because it uses HAMTs (Hash Array Mapped Trie) internally. They enable much faster copies of immutable data than copy-on-write does.

Your other points are good ones, I just don’t want people to be put off by copy-on-write performance assumptions. You take a ~50% performance hit from choosing Clojure over Java, but the gains in dev speed, maintenance, robustness, and flexibility to changing requirements are supposed to outweigh that. Especially when you include simpler parallelization, which you covered with thread safety.



There was an issue I ran into with regular Java, JDOM 2 Documents, One thing saves a reference, the other thing snips a piece out to use in the response... oops, the first reference points to a snipped Document. Worse, that behaviour changed without interface changes between JDOM 1 and 2, and it mattered to the code I was editing. Easy enough to fix with a ".clone()" but still... it's not just parallelisation. Immutable data would mean immutable to weird action at a distance like that. Thankfully the unit tests caught it before it could have gone live.

(More precise issue... JDOM 1 lets you splice a piece of A into B while it still is part of A. JDOM 2 insists it be detached first. Detaching it removes it, and that removal can be seen through a reference.)


Huh. I don’t know enough about JDOM to ask more than stupid questions, especially when we’re talking about two different languages on the same VM. So please bear with me or ignore at your leisure.

This all happened within Clojure? Their Java interop is reportedly good, but the docs also say you lose the immutability safeguards when you interact directly with Java classes. I dunno if “regular Java” means literally that, or while working with Java inside of Clojure. Which is it?

“One thing saves a reference” - if this was interop, did you convert that to a Clojure data structure as early as possible, and do no more interop after that until a final return?

I’ve avoided deep interop so far, so I don’t understand the mechanics of the interface, and I’m not clear if your response is about that.


Sorry for being confusing, it was intended as an illustration of why Clojure's approach is good.

Non-immutable data being shared around is basically a recipe for weird action at a distance, is the point.

In what was intended to be a "compatible API, just change the imports" update, code broke because an unchecked invariant became a checked one, and then broke again because the workaround mutated data that was being referred to somewhere else.




Consider applying for YC's Fall 2026 batch! Applications are open till July 27.

Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: