I'm looking to refactor an existing design; to move a bunch of stuff out of a database and into memory where it should be (There are many reasons the DB approch is dangerous as it is now). My first act was to take all the existing objects and expand more state to them. The previous objects new only their parents, and that was it. From the youngest child you could walk up to find parents, but you couldn't ask "what edges are on this node" at all.

I changed things to make state more accessible from every object. Now each object effectively knows of it's parent and all of it's children. I thought this was an obvious simplification that would make storing things in memory much easier. The problem is that I need to be able to construct objects without modifying my model, untill addToModel is called, which means I need to be able to construct objects in one state, and then update some of their state to be consistent with the Model's state and properly represent all the interconnectivity (node has to be informed when an edge is added, edge needs to know it's paths etc etc).

This proved surprisingly complicated to keep consistent. I end up with either encapsulation issues (like assuming each object knows not to call the package scope methods that change memory from public methods that shouldn't be able to change state), as well as a concern about aliasing (what if someone creates a new Node A with no connections, when my Model says node A should be connected to B, C, and E?). I thought of many approches that work, but none feel 'clean'. Is the issue that I"m trying to make my objects too aware of state, and thus putting too much effort on my model to maintain this state?

  • It seems you are trying to create an oriented graph. Try to search for or-graph implementations to see what approaches can be used. Besides, there are many known algorithms for graph, which might turn useful to implement the constraints you have.
    – superM
    Apr 29 '13 at 15:31

This is why linked lists are not defaultly doubly linked. It seems at first glance that doubly linked would be easier, but pretty quickly you realize the actual implementation for a singly linked list is considerably simpler.

So you refer to the model in this way being an obvious simplification; but are coming to realize, that's not actually the case. The less any given object knows, the simpler it's implementation, and maintenance in the long term will be. This is why it's best to make objects only know so much as is necessary, then add state/memoization only when tasks working with the model become overly difficult. Weigh the scenarios you need account for with each piece of state your add to an object against the implementation necessary to deal without that bit of state added to the object.

Another way of ensuring simpler maintenance of your model is to make all objects that won't need necessary mutability immutable. This again reduces the amount of implementation as those parts of your models don't need to account for update scenarios.

  • yes I did try to use immutable as much as I can, but many things proved not to work with an immutable approch as well as I would like. Still the general concept you said is true.
    – dsollen
    Apr 29 '13 at 20:18

You can externalize edges from your nodes and use something else to modify/query connections. For example look at JUNG (java graph library) where nodes and edges can be anything and you tell graph that it should contain node(s) and edges between them. And there are multiple implementations (build in are IIRC dense and sparse, but you can create your own). Anyone with acces to graph can query it and change it, but you could create some graph view (something with only query methods and pass only it outside, not the graph object itself).

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.