• Post Reply Bookmark Topic Watch Topic
  • New Topic
programming forums Java Mobile Certification Databases Caching Books Engineering Micro Controllers OS Languages Paradigms IDEs Build Tools Frameworks Application Servers Open Source This Site Careers Other Pie Elite all forums
this forum made possible by our volunteer staff, including ...
Marshals:
  • Campbell Ritchie
  • Jeanne Boyarsky
  • Ron McLeod
  • Paul Clapham
  • Liutauras Vilda
Sheriffs:
  • paul wheaton
  • Rob Spoor
  • Devaka Cooray
Saloon Keepers:
  • Stephan van Hulst
  • Tim Holloway
  • Carey Brown
  • Frits Walraven
  • Tim Moores
Bartenders:
  • Mikalai Zaikin

Is a cycle a bad thing?

 
Ranch Hand
Posts: 223
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hi all,
my metric tool tells me that I have a software cycle on package level.
Now I am wondering if a cycle is a bad thing in general?
Here is a very simple example of a cycle.
Note that both classes are in the SAME package.

The metric tool tells me that I have a cycle on package level,
which is true since Person uses Family and the other way around too,
Family uses Person.
I tried to resolve the cycle by introducing interfaces such as
IPerson and IFamily (in the same package) but obviously it created
another cycle for IPerson and IFamily.
Now I wonder if the cycle I produced is bad, or in other words,
are there cycles that are ok? If cycles are generally bad how can
I resolve the sample shown above?
 
author
Posts: 14112
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Dependency cycles for classes can't fully be avoided. Package cycles are a different beast, though.
"Agile Software Development" by Robert C. Martin covers this and other design principles very nicely, by the way.
 
(instanceof Sidekick)
Posts: 8791
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Re your problem with interfaces ... it becomes an issue of which package should own the interfaces.
If you package an interface with the objects that implement it, you may be emphasizing reuse. You could shrink wrap the package and sell it to people and they could use it. Sometimes this is good - for example we'd like to reuse a business service from different user interfaces (web, fat client, IVR, etc)
If you package an interface with the objects that CALL it, you may be emphasizing system stability. The policy package (what I want to do) might own the interface and the mechanism package (how I get it done) has a dependency on policy. That's likely to follow the rule of less stable depends on more stable. I can extend a core insurance process to new contract types without touching core code because all contract types implement an interface owned by the core process.
Look around on Google for the Dependency Inversion Principle. See how my example inverted the dependency? That's a way around cycles. Oh, and if Person and Family appear to be peers with equal place in the abstract/stable scale, maybe they should both depend on some new package. Something to think about. Hope that all helps!
[ November 26, 2003: Message edited by: Stan James ]
 
David Follow
Ranch Hand
Posts: 223
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I see what you mean.
The dependency inversion principal is discussed in detail in
Robert C. Martin's book (Agile Software Development).
However, I don't quit think it applies to my simple problem from
above where Object A uses Object B and the other way around,
where Object B uses Object A. I understand that I can return an interface
instead of a concret class but in the method body I have to instanciate
(and return) the concrete class. And this is exactly what causes my
dependency cycle.

on the other had I have

In both cases I have to get concrete and return real instances
of Person or Family respectivly. And this gives me a dependency
cycle which I would like to resolve, but how?
 
Ranch Hand
Posts: 1923
Scala Postgres Database Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I don't understand, why a Family always contains 5 persons, and why both methods return 'new XY '.
I would understand, if a Family could be created

Of course this is simplified...
The person too:

Of course, the dependencies are cyclic too.
Perhaps you didn't create allways new Classes all the time?
 
David Follow
Ranch Hand
Posts: 223
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Of course your solution is more sophisticated, no doubt, but like
you said yourself, you still have a dependency cycle.
In this case, I wonder if a cycle is a bad thing or are there
cycles that are "good" or "needed" in some certain way or do I ALWAYS
have to try to avoid dependency cylces?
 
Stan James
(instanceof Sidekick)
Posts: 8791
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Cycles between classes in a package are common, and not necessarily harmful. But, there are usually ways to get around them if you really want to. For example, to have Family avoid making concrete Person objects, Family could call a PersonFactory which might be the only class that actually knows about concrete Person classes.
Cycles and wrong directions between packages are riskier, and can hamper your ability to extend the system later. I finally got OpenOffice so I could convert my DIP presentation to HTML here: http://www.surfscranton.com/Architecture/DependencyInversion.htm See if that helps or just confuses more.
 
David Follow
Ranch Hand
Posts: 223
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Stan,
thanks for the link. I see you refer to "Agile Software Development".
I got a chance to flip through the book and it is indeed an excellent book.
A must for every software developer/architect.
I agree that cyclic dependency within the same package can happen, but
should be the exception and not the first choice approach. The use of a factory
can indeed solve the problem.
On the other hand, cycles over different packages is a bad thing and should
be avoided at all. The book gives a nice approach of avoiding
cycles through the dependency inversion principal.
I will play around with it for a while to see if it applies to a real
world project.
 
Stan James
(instanceof Sidekick)
Posts: 8791
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Another interesting line of study is eliminating giant case statements, especially based on instanceOf or what kind of class you're dealing with. Look for refactoring patterns that start with "replace case statement with ..." Many of these remove dependencies through polymorphism or factories or some othe cool mechanism and have ideas that can be applied to the package cycle problem.
 
David Follow
Ranch Hand
Posts: 223
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Can you recommand any interessting literature/Links on refactoring?
 
With a little knowledge, a cast iron skillet is non-stick and lasts a lifetime.
reply
    Bookmark Topic Watch Topic
  • New Topic