|
Everyone’s had to deal with it. The big, nasty project, where everything links to everything, and anything you do can have seemingly random effects in apparently unrelated areas. So, let’s look at some ways to avoid that. But first, let’s define what we mean by “coupled.â€Â Two pieces of code (classes, modules, whatever) are coupled if they have to know how each other work in order to function. Couplings can exist one-way, or two-way. Some coupling is good – programs probably wouldn’t do much without them. Where the sinister evil starts to sneak in is unnecessary coupling, and unnecessary intimacy. To start with, let’s look at a piece of code: public class SomeClass {    public void DoSomethingToCharacter(Character c)    {        string username = c.Connection.User.Name;    } } Okay, so it doesn’t do much at this point. But it’s a pretty good start as to where there might be a problem. And what problem is that? Well, it’s pretty apparent that this method needs to do something with the character’s name. But to get that information, we have to go through both the connection and user properties. This opens us up to problems. First, it means we have a physical dependency on those classes, which can create compilation time issues. Secondly, it means that to get the data we want, we have to know quite a bit about the class we’re using. We have to know that it has a connection object, and that that object has a user object, and that object has a name. I don’t want to know that much. I just want the user name from the character! The worst problem is that we open ourselves up to build breaks every time we use this access pattern. If any of those classes change, we break. And probably in lots and lots of places. Let’s look at an alternate: public class SomeClass { public void DoSomethingToCharacter(Character c) { string username = c.UserName; } } Ah, yes. Isn’t that pretty? Now our code only cares about the character we class. We don’t know how many layers of ugliness are going on underneath, and we don’t need to. Even better, if one of them breaks, the damage is going to be limited to inside the character class itself – which means an obvious place to fix, instead of hunting down those chains of objects all over your codebase. Oh, and for what it’s worth – those chains of objects have a name. They’re called “train wrecks,†after all of those objects smashed into each other. It’s not a term of endearment. And what I’ve been describing has a name as well – it’s called the Law of Demeter. It basically states that a given method can only use methods internal to objects it owns, on objects that are passed in, or on objects it directly creates. Source : http://www.wrong.net/2007/12/02/decoupling-code/ |