in reply to Advisability of circular dependencies in packages
Well structured code has good interfaces between sections, hiding detail. The responsibility of a section and its underlying assumptions is understood in terms of it's interface and accompanying documentation. (OK, yes, abstractions are partially leaky in practice, but to the extent that they aren't, you win).
Where you lack this, you need to read and attempt to understand much more code to get the picture of what is going on.
One way you can evolve a codebase is to try and identify candidates for such interfaces (configuration and logging are often a good place to start). If you find somewhere where you can seperate off a chunk of functionality behind a decent interface, you can write your new interface in terms of the old functionality, i.e. you can proxy back to the existing (proven) code whilst gaining the benefit of having clearer expression of intent in your newer code.
You can document and unit test these interfaces, etc and get benefits that way.
Over time, as you touch older code, you might migrate it over to the new interface, reducing the amount of code which depends on the old codebase directly.
Possibly, you could re-implement the interface in terms of new, clean code (relying on your tests to see if you've broken anything). You can then either ditch the old code (if no-one else is using it) or proxy the old methods onto the new code if possible.
So, I think a large part of design (including retro-fitted design) is coming up with good interfaces between sections of code. The above is one way of retro-fitting such design on existing code.
Also - IMHO an interface should provide the least functionality you can get away with for the task at hand. If you have an internal function (_foo) which you think might be handy to make public, resist the temptation - the smaller the interface the easier it is to understand.
If you do want that function in the interface in the future, it's easy enough to rename (because it's only used internally in that module). The reverse isn't true. Taking a method private (say because you want to change an internal algorithm) is much harder - you have to find and change all occurences of the code which uses it (or come up with a reasonable way to fake it in the new implementation).
|
|---|
| Replies are listed 'Best First'. | |
|---|---|
|
Re^2: Advisability of circular dependencies in packages
by roboticus (Chancellor) on Nov 13, 2006 at 18:37 UTC |