0

As far as I know, circular dependencies are something to be avoided, yet I find myself often in a situation where I've got some Object, and an ObjectManager, that is supposed to "oversee" all the Objects, and provide methods to aggregate these Object's and so on.

Example:

  • Object that has a position and can move itself
  • ObjectManager with methods like getAllObjects and getAllObjectsAtPosition(x, y)

ObjectManager needs to have a list of Object references, and Object needs a reference to ObjectManager, so it can notify the ObjectManager that it has changed its position (so ObjectManager can, for example, update its hashmap with position : Object pairs, so getAllObjectsAtPosition is not linear)

Does it make to have a circular dependency here? If not, how should it be avoided?

asked Apr 19, 2021 at 11:06
1
  • One solution would be to put a GetPosition() function on the Object which is called by the ObjectManager when the manager needs to know positions. (see "The Hollywood Principle" thephantomprogrammer.blogspot.com/2015/08/…) Commented Apr 22, 2021 at 9:46

1 Answer 1

2

Yes, circular dependencies are bad. The reason for that is you can't really change or even understand the one without the other, which kills maintainability.

Second, there are lots of ways to solve a circular dependency, but none is really generic. So you'll have to design your way around it case by case.

With your positions example, I offer you these alternatives:

  1. Try to get the position out of Object, so it's only in ObjectManager.
  2. Have the ObjectManager wrap all returned Object references with a Facade that updates ObjectManager's own positions map when a move (or similar) is called on individual Objects.
  3. Couple the Object with ObjectManager through an indirection, like a "listener" interface or event bus, or similar. I would note this complicates things significantly, so it should be the very last resort. This is basically "inverting" the dependencies in one direction.
  4. Have the Object itself be a part of (inner class of) ObjectManager.
  5. Design the whole thing differently, find different abstractions.

Also note that Object and ObjectManager are really bad names, I assume you picked those just for demonstrating the hierarchical relationship between them. Don't actually name things "Manager", that's so 2000s. :)

answered Apr 19, 2021 at 11:44
2
  • Thank you. Also, I wanted Object to fire an event whenever it changes its position, rather than keep an explicit reference to the manager. ObjectManager would listen to these events. I assume this is the third option on your list? Commented Apr 19, 2021 at 11:50
  • 1
    Yes, that's what I've meant. Again, having events still creates a coupling, and now this coupling is less visible. So it's a trade-off. Commented Apr 19, 2021 at 11:59

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.