4 ms·
It's dificult to refute your argument because I don't understand your points: > Because of the locality aspect, people will assume that it's 'free' to look up
by zasdffaa 4y ago
It's dificult to refute your argument because I don't understand your points:
> Because of the locality aspect, people will assume that it's 'free' to look up a value multiple times instead of passing these data dependencies between the relevant methods
what does that even mean? What does 'data dependencies' mean specicially?
> then you can end up evicting data in the middle of a transaction
So in the middle of a transaction, instead of looking up data from a key - very cheap - you should do ... what? Recalculate it instead?
> The less obvious consequence is now you have concurrency bugs, because the code assumes that decisions made about the data will go the same way on each call, but due to eviction, two halves of the transaction may make conflicting decisions with undefined behavior
Assuming I even understand this, you are saying where there's concurrencty there's a risk of pulling stale data out of a cache. Well, true. That's just something you have to be careful of. Add a Tx reference to the cache key.
> Once you introduce caching you poison the performance well.
Not my experience at all. I can't understand why you're saying this.
> Flame charts lie when cache is used
How so?
> and after people rely on the cache it is lying in the other direction when the cache is off, because you're calling that path 5 times now and it's swamping other bottlenecks
I've no idea what this means
> This is what I really mean when I say it's a weapon of last resort. Because once you use it, it attempts to take any other options off the table
Heh! Absolutely not! Other optimisations are orthogonal to caching IME:
Better algo - orthogonal
Go lower level - orthogonal
Go multicore - orthogonal
Noobish SQL query is begging for a rewrite - orthogonal
Use L1/2/3/ chip cache better, or RAM, by careful data layout - orthogonal
Use a better library - orthogonal
Use better data structure eg. than linked list - orthogonal
- svieira 4y ago>> Because of the locality aspect, people will assume that it's 'free' to look up a value multiple times instead of passing these data dependencies between the relevant methods > what does that even mean? What does 'data dependencies' mean specicially? It means that instead of having a method like `entryPoint(int)` that looks up a `Foo` by id and then passes the `Foo` around (`verify(Foo)`, `Foo update(Foo)`) you instead wind up with a system that passes around an `int` (`verify(int)`, `/* Unused */ Foo update(int)`) and each layer then looks up `Foo` in the `FooService` (because `FooService` has a cache and subsequent lookups should be essentially-free). Even worse when `FooService` is abstracted behind a thread-local like `ThreadLocal<Foo> currentFoo`, the implementation of which is `fooService.findById(currentFooId.get()) /* cheap, because fooService has a cache */`. My own take on this is that caches are global-by-default when you really want local-by-default (e. g. dynamic programming instead of a `static final Cache theCacheForTheEntireProgram`). Local-by-default caches are easy to make transactional (when the call stack returns the cache is gone) and don't grow in an unbounded manner in the general case.
- hinkley 4y agoYes! Local by default also has the feature/problem of making you look at the scale of the data involved in your query up front, before it's having a 100-1000 req/s hitting it in production. It's harder to pretend this large dependency graph will just magically take care of itself (or worse, be someone else's problem after you've declared victory) when it's staring you in the face.