I read about Flyweight design pattern and got to know that it stores the objects that can be shared so as to save on heap usage. Java cache also saves the objects that can be reused later so as to save memory. Then what is the real difference between Flyweight design pattern and java cache ?
Let's assume "Java cache" is an object pool (or object pool pattern).
I think the difference lies in the understanding of objects being cached are singleton or not.
In the flyweight pattern, you use the same object fetched from "the factory" by potentially multiple clients. That requires different way of managing stuff (like concurrency, client-related work etc.). For example, if you fetch the same flyweight object (let's say a button) in multiple UI clients/viewports which are visible at the same time, then you end up with manipulating the same object (for example the button text) which may create inconsistency on these different UIs/viewports. That won't happen since the pool/cache will return you a separate object each time you ask for an object.
Regarding being immutable, I've encountered couple of examples on the web which includes extrinsic/changing state in the flyweight object. Well, I don't think it's completely wrong to include it as a part of a flyweight object, since the point is reducing the memory footprint, as long as you can manage objects properly. But I also think that it's totally open to discussion.