Dealing with Dependencies

Compositional programming style

In the object oriented programming style, it’s preferable to split functionality out to multiple objects, that can work together to solve a single task. Taken to the extreme, this results in more, but smaller, classes and generally relies less on inheritance and more on composition. In lack of better words, I’ll call this compositional programming style. It’s a style which is usually more prevalent with experienced programmers.

For someone coming from an imperative style of programming, this style can appear abstract and confusing, but the benefits are in the flexibility of the code. If different objects are related through composition, parts can be replaced, without changing the code. This makes it easier to reuse components, and to hook into the code, by providing a wrapper here or there. This is especially useful during testing, since it becomes easier to mock out external dependencies (Such as a database or an smtp server).

There is, however, a dark side to composition — dependencies.

So what is a dependency?

For the sake of this post, I’ll use a rather naïve example. Assume, that we were building an addressbook application. This would feature an entity of type Person. In our code, we might have a class for accessing an underlying table in the database. Initially, it might look like this:


class PersonGateway {
  protected $db;
  function __construct() {
    $this->db = new PDO("mysql:host=localhost;dbname=addressbook", "root", "secret");
  }
  function getPerson($id) {
    $stmt = $this->db->prepare("select * from persons where id = :id");
    $stmt->execute(array(':id' => $id));
    return $stmt->fetch();
  }
}

However, we also need an entity of type Address, and since this also needs access to the database, we’ll now end up with two connections, if we implement it in the same way. What we need, is a single database object, which our two gateway classes can share. This kind of object is called a dependency[1] — The gateway classes are called dependants.

Notes:
[1] It was pointed out to me in the comments, that I’m using dependency in a slightly different meaning here, than it is used in UML. The kind of dependency, I’m talking about, is working on an object instance level — not the class level. See honeymonster’s nice explanation.

Would you pass me that dependency, please?

There are roughly speaking just two ways, that a dependency can be satisfied. Either the dependency is obtained through a global symbol[2] or it is passed in from the outside. Global symbols are the least abstract method and therefore often appeals to lesser experienced programmers. However, their concreteness also makes them very inflexible. Global symbols are generally hard or impossible to change at runtime, so a lot of the benefits of aggregation is lost. Further, globals hide side-effects, making them ideal vessels for introducing hard-to-spot bugs into your application. For these reasons, we’ll pass in the dependencies, making our gateway look like this:


class PersonGateway {
  protected $db;
  function __construct($db) {
    $this->db = $db;
  }
  ...
}

Notes:
[2] To global symbols, I count global variables, constants or any kind of static member (Including the infamous Singleton)

Leaky dependencies

As a general rule, dependency pasing is a good tool. In our above example, we could easily replace the database with a mock, if we wanted to test it. It does come at a management cost however. Presumably we would now go and write some application, which relies on our gateway. Some place down the road, we figure that we need to add an identitymap to the gateway. As the compositional style prescribes, we provide these as external dependencies, but to do so, we change the constructor of the gateway.

We now have to go back and edit all places, where the gateway is instantiated and provide the new dependencies. This is not good — The user shouldn’t be bothered with interface changes, just because we are redefining the internal behaviour of our component. And there’s another problem too. The user now has to be aware of cryptic sounding classes, which aren’t really any concern of his. We have a lack of encapsulation.

Writing a container

There are different ways of solving this problem, without resolving to global symbols, but what they all have in common, is that they hide the constructor away in a factory. In doing so, the dependencies can be resolved in one place, hidden away from the user, who couldn’t care less about the ugly details. For our example, the container might look like this:


class Container {
  function new_PDO() {
    return new PDO("mysql:host=localhost;dbname=addressbook", "root", "secret");
  }
  function new_PersonGateway() {
    return new PersonGateway($this->new_PDO(), $this->new_IdentityMap());
  }
  function new_AddressGateway() {
    return new AddressGateway($this->new_PDO(), $this->new_IdentityMap());
  }
}

But wait a second. This container is creating two database connections, when we already decided that we’d want just one. We do however want two distinct instances of identymap, since they should track different types.

So as it turns out, classes can be divided into two kinds, based on their uniqueness in the application. There are shared objects, such as the database connection and there are transient objects, such as the identitymap. And further, the gateways them selves are also shared — We wouldn’t want multiple copies of these.

To address this, we’ll split our container up into two different parts: A container and a factory. The container holds the shared instances and provides the public facing interface, while the factory contains methods for creating instances. A simple implementation might look this way:


class Container {
  protected $factory;
  protected $instances = array();
  function __construct($factory) {
    $this->factory = $factory;
  }
  function get($classname) {
    $classname = strtolower($classname);
    if (!isset($this->instances[$classname]) {
      $this->instances[$classname] = $this->create($classname);
    }
    return $this->instances[$classname];
  }
  function create($classname) {
    return $this->factory->{'new_'.$classname}($this);
  }
}
class Factory {
  function new_PDO($container) {
    return new PDO("mysql:host=localhost;dbname=addressbook", "root", "secret");
  }
  function new_PersonGateway($container) {
    return new PersonGateway($container->get('PDO'), $container->create('IdentityMap'));
  }
  function new_AddressGateway($container) {
    return new AddressGateway($container->get('PDO'), $container->create('IdentityMap'));
  }
}

Putting the container to use

There are room for improvements on this, but we already have a very solid container to use. One big advantage of separating the factory from the container, is that it’s trivial to stub out selected classes, during testing. Say I wanted to write a unittest for the PersonGateway class and for this, I wanted to replace the database with a stub. Here’s how:


class TestFactory extends Factory {
  function new_PDO($container) {
    return new MockPdo();
  }
}
class TestOfPersonGateway extends UnitTestCase {
  function setUp() {
    $this->container = new Container(new TestFactory());
  }
  function test_finder_selects_from_database() {
    $statement = new MockPdoStatement();
    $statement->expectOnce("execute");
    $this->container->get('PDO')->expectOnce("prepare");
    $this->container->get('PDO')->setReturnValue("prepare", $statement);
    $gateway = $this->container->get('PersonGateway');
    $gateway->getPerson(42);
  }
}

Since the test case uses a subclass of the real factory, it doesn’t need to be updated each time I decide to change the dependencies of my class. There is no hidden side effects either; The container contains any shared instances, so for each test I get a completely fresh setup.

But that’s not all — Order today, and get a namespace tossed in for free!

PHP 5.3 is scheduled to be out soon and one of the most anticipated improvements is the introduction of namespaces. With just a single global namespace, PHP classes have a tendency to get really long-winded, to avoid nameclashes. Namespaces allows us to use shorter names to address classes, while still avoiding nameclashes.

This feature has been so requested for, that it has been pushed back to PHP 5.3, even though it was originally planned to bew introduced with PHP 6. We don’t need to wait for PHP 5.3 though. With our container above, it’s easy to write a wrapper, which provides a namespace for us:


class Namespace {
  protected $prefix;
  protected $container;
  function __construct($prefix, $container) {
    $this->prefix = rtrim($prefix, '_') . '_';
    $this->container = $container;
  }
  function get($classname) {
    return $this->container->get($this->prefix . $classname);
  }
  function create($classname) {
    return $this->container->create($this->prefix . $classname);
  }
}

Assuming we’ve written a factory already, we can now use the Zend framework, without the extremely long clasnames:


$container = new Namespace("Zend_Cache_Backend", $container);
$memcached = $container->get("Memcached");

Of course real, language supported namespaces also buffer away other symbols than just class names, but in object oriented code, those will be few anyway. The exception is the legacy procedural libraries of PHP, which can’t be avoided. In a recent post, Mike Naberezny described a way to deal with these, in a way quite similar to our container.

This post has been translated into German.

Free book: Jump Start HTML5 Basics

Grab a free copy of one our latest ebooks! Packed with hints and tips on HTML5's most powerful new features.

  • giorgio_c

    Great article, really liked it.

  • http://www.tonymarston.net Tony Marston

    All that code just to avoid using a global symbol? What rubbish! When I want an instance of my DAO I simply use a singleton, which guarantees that I always reuse a single instance instead of creating duplicates. That is what the singleton is for, for crissake!

    I find your arguments against globals – “least abstract method”, “very inflexible”, “hard or impossible to change at runtime” – to be quite fatuous. Sure, it is possble for a bad programmer to f*ck using globals, but guess what? It is possible for a bad programmer to f*ck up whatever you use. The only solution is not to emply bad programmers.

    I’m afraid my one-line call to a singleton beats using your factories and containers on any day of the week.

  • sike

    tony : this is a highly debatable topic but i think you know why allowing “global” access to parts of your code is a bad idea. so i take your comment as your own personal way of solving the problem kyper discussed.
    but please stop making bad arguments – you seem like a guy that did not fully understand the object oriented way of programming which is what kyper is talking about : solving problems in a good oo manner.

    chris

  • kyberfabrikken

    All that code just to avoid using a global symbol? What rubbish!

    First of all, it isn’t really all that much code. The simple container, I use in this article, is 28 lines, of which the majority (class Container) is reusable. In comparison, each singleton takes up about half a dozen of lines. Not that LOC is a very good measure of quality on its own.

    The desire to avoid global symbols isn’t as arbitrary, as you make it sound. If the application mixes global and local symbols, you raise the overall complexity of the application. Using local symbols may add a bit of extra work, but the benefit is that any side effects become explicitly apparent. This leads to code, which is easier to maintain, to test and to reuse.

    In the procedural style of programming, it’s very hard to avoid global symbols, so if that’s your offset, you may be used to living with them. What OOP offers you (among other things), is a way to avoid globals completely.

  • Bart
  • honeymonster

    kyber, I think you should realize that you use the term dependency in a rather unorthodox way. In UML a dependency i simply defined as

    A relationship between two elements in which a change to one element (the supplier) may affect or supply information needed by the other element.

    and dependency injection simply refers to the technique where an object (the dependant) which needs to manipulate another object (the dependee) receives that object through either its constructor or through a public setter.

    Thus, by using this term for the situation where two object needs to share a third object you are using an otherwise rater well-defined term to mean something different.

    I would just say that the two object has a shared reference. Of course when they need a shared reference they cannot simply create it themselves; they must retrieve their references in some other way, of which dependency injection is one.

  • http://www.tonymarston.net Tony Marston

    sike: this is a highly debatable topic but i think you know why allowing “global” access to parts of your code is a bad idea.

    me: I have used languages where all variables passed between components were global, so I know how bad this can be. However, even with languages that offer non-global alternatives there are circumstances when the use of a global is the most efficient solution. I totally disagree with the notion that “all globals are bad” just as I disagree with the notion that “everything is an object”.

    sike: you seem like a guy that did not fully understand the object oriented way of programming

    me: When you say “not fully understand” what you really mean is that my approach is not the same as yours and therefore somehow inferior or deficient. It is not inferior, it is merely different. I always look for the simplest implementation, not the most complicated, and that is the only thing which separates me from those who call themselves “real” OO programmers.

    kyberfabrikken: In comparison, each singleton takes up about half a dozen of lines.

    me: What do you mean “each singleton”? I make do with only one singleton class in my entire application. If you have more than one then you have a poor understanding of code reuse.

    kyberfabrikken: The desire to avoid global symbols isn’t as arbitrary as you make it sound.

    me: Yes it is. The decision whether to use or not use globals is a matter of personal choice, therefore is totally arbitrary.

    kyberfabrikken: If the application mixes global and local symbols, you raise the overall complexity of the application.

    me: I disagree. A solution which uses fewer lines of code makes the application less complex and easier to maintain.

    kyberfabrikken: What OOP offers you (among other things), is a way to avoid globals completely.

    me: If the side effect of avoiding globals completely is (a) more code and (b) more complex code then I prefer to stick with the simple solution. That is what the KISS principle is all about.

  • kyberfabrikken

    @honeymonster
    Thanks for pointing that out — Picking the right words is important and I am using the word dependency in a narrow sense, which may not be entirely clear. But I still lack a better word, to cover the same meaning. Shared reference isn’t entirely covering, as it captures a concrete type of dependency; I need something to cover both shared references and transient references.

  • kyberfabrikken

    What do you mean “each singleton”? I make do with only one singleton class in my entire application. If you have more than one then you have a poor understanding of code reuse.

    The following lead me to believe, that you would have a singleton for each DAO (And presumably for other classes as well):

    When I want an instance of my DAO I simply use a singleton (…)

    Is that a misinterpretation?

    If the side effect of avoiding globals completely is (a) more code and (b) more complex code then I prefer to stick with the simple solution. That is what the KISS principle is all about.

    I think, you’re over-simplifying the nature of complexity. More code is not a problem in itself. A larger interface is.
    Yes, a factory results in a bit more indirection (more code to execute), but the interface is smaller.

  • honeymonster

    @kyber. Yes re-reading your posting I can see that I may have homed in on the fact that you explain dependencies in the context of shared dependencies/references. Obviously, that does not exclude using the term in its narrow definition. You were using the term rather than defining it. My bad.

    For what it is worth I feel that “dependency injection” is poorly aligned with the way dependency is defined by UML. In UML the term is used between concepts (classes). If a certain type contains properties of another type the former is said to be depending on the latter, ie a dependency. In the context of dependency injection we are operating on an instance level. I feel as if “reference injection” would be a more appropriate name for it. But that battle is long lost. It never hurts to become aware of such alignment discrepancies, though.

    A class can have a dependency on another class without holding (in the structural sense) a reference. An obvious example is when a method (instance or class level) expects another class/interface as parameter. Another example would be a method which simply uses another class for a local variable. It does not hold a reference but it does have a dependency.

    What you are talking about I would term external references or maybe just references. Some external references are shared, some are not. Either way, instances of the referring type must have some way it can obtain the references, as you explain.

  • http://www.tonymarston.net Tony Marston

    kyberfabrikken: The following lead me to believe, that you would have a singleton for each DAO (And presumably for other classes as well):

    When I want an instance of my DAO I simply use a singleton (…)

    me: Each DAO? You mean I’m supposed to have more than one? How neanderthal. I do not have a separate DAO for each database table, or even for each database, but a separate DAO for each database engine (one for MySQL, one for PostgreSQL, one for Oracle). As an entire application usually runs with a single database engine I therefore have a single DAO for the entire application.

    I also have a single singleton class for the entire application, and not a singleton method within each class. This is what “code reusability” is supposed to be all about, and it’s the opposite of “code duplication”.

  • honeymonster

    @Tony Marston

    Composability and (architectural) scalability. With your global design (global DAO and a single, central singleton) your code

    1) Is less composable. Because your classes generally rely on finding this singleton (a registry, really) you have a strong dependency on that singleton. You also have classes built with the notion of global resources. Those classes cannot be reused in a setting where you may want a non-global behavior. Individual classes cannot be used in another setting without having the singleton also. If you combine with other classes which were designed the same way (but with another singleton in mind) you start feeling the pain. Now you need to either combine the singletons but still retain two global references or accept that the singletons cannot coordinate the resources they manage.

    2) Does not scale well with project size/complexity. The “global singleton” will bloat, taking on responsibilities for handing out objects with many different purposes. You cannot evaluate part of the code using fixtures (e.g. during debugging) while leaving the rest to behave as usual.

    Now, these limitations may not apply to projects of the size you are dealing with. But consider if framework developers were all using the same approach. You would then end up with all different kind of global singleton registries. If framework A uses singleton SA, framework B uses SB and your own code X uses SX; and all of them obtains database connections through their respective singletons, you really have no easy path to make SA, SB and SX work against the same pool of connections/objects.

    Your approach (a global registry) is a well-known one, and it is perfectly viable in a number of situations. But immediately dissing an alternative technique without recognizing that it may be viable in other situations comes across as very confrontational and somewhat immature in the field of CS.

  • Pingback: SitePoint PHP Blog: Dealing with Dependencies | Development Blog With Code Updates : Developercast.com

  • http://www.tonymarston.net Tony Marston

    honeymonster: your code is less composable.

    me: WTF does that mean?

    honeymonster: Because your classes generally rely on finding this singleton (a registry, really) you have a strong dependency on that singleton.

    me: you are obviuosly using a peculiar definition of the term “dependency”. No class is dependent on the singleton class.

    honeymonster: You also have classes built with the notion of global resources. Those classes cannot be reused in a setting where you may want a non-global behavior. Individual classes cannot be used in another setting without having the singleton also.

    me: Rubbish. It is not up to each class whether it is provided as a single instance, it is up to the calling module. It is the caller which makes that decision, and either uses the singleton class OR creates its own unoque instance.

    honeymonster: your code does not scale well with project size/complexity. The “global singleton” will bloat, taking on responsibilities for handing out objects with many different purposes. You cannot evaluate part of the code using fixtures (e.g. during debugging) while leaving the rest to behave as usual.

    me: absolute rubbish! My current applcation has over 130 tables, 230 relationships and over 1000 tasks, and I have NEVER encountered any problems with my singleton class, nor have I found any problems when debugging.

    honeymonster: Your approach (a global registry) is a well-known one, and it is perfectly viable in a number of situations. But immediately dissing an alternative technique without recognizing that it may be viable in other situations comes across as very confrontational and somewhat immature in the field of CS.

    me: I will always dis a technique which is more complicated that it need be, or which conforms to arbitrary rules drawn up by some so-called guru. I always prefer the simple solution because simple is maintainable, simple is efficient, and simple scales a darn site more than complexity. I think that turning your back on a simple solution is more of a sign of immaturity than embracing a simple solution.

  • rojoca

    One unfortunate side effect of using Container is your favorite editor’s code completion goes out the window.

    I wouldn’t completely rule out interfaces – I know no one’s saying that – it’s just that they’re supposed to be concrete – this object does this.

    Rather than “change the constructor of the gateway”, if your gateway is an interface, re-implement it with your new internal dependencies. Use a factory to serve the appropriate implementation to the user.

    Not quite as elegant maybe. If your interfaces are changing all the time (hopefully not all of them are) a container type approach is probably a good idea.

  • kyberfabrikken

    @Tony Marston
    I’m afraid, we disagree on some fundamental pre-requisites here. If you aren’t going to write in an object oriented style, then obviously, you have no need for an object oriented solution.
    Somehow, I get the feeling, that you are deliberately steering this discussion off, to pursue some alternative agenda. I have no interest in participating in that, so I think we’re better off saying, that we disagree and leave it with that.

  • Pingback: links for 2008-02-05

  • kyberfabrikken

    One unfortunate side effect of using Container is your favorite editor’s code completion goes out the window.

    That is true — I didn’t think about that, because I don’t use an editor, which does that kind of magic. Ultimately it’s a limitation of the tool. It’s inherently difficult (impossible even) to do static code analysis on a dynamically typed language. Perhaps the vendors of these IDE’s should allow the user to hook in small scriptlets, to help determine the type. But until that happens, you have a point.

  • Pingback:   SitePoint PHP Blog: Dealing with Dependencies by Joe McLaughlin’s Blog

  • http://www.tonymarston.net Tony Marston

    kyberfabrikken: I’m afraid, we disagree on some fundamental pre-requisites here. If you aren’t going to write in an object oriented style, then obviously, you have no need for an object oriented solution.

    me: Who says I’m not writing in an object oriented style? My “style” may be different from yours, but that does not make it less object oriented.

    kyberfabrikken: Somehow, I get the feeling, that you are deliberately steering this discussion off, to pursue some alternative agenda.

    me: No I’m not. This “solution” was proposed as a way to avoid the use of global objects, and my argument is that (a) there is no rule which says that I must not use global objects, and (b) if the most efficient solution involves the use of globals then so be it. I am certainly not going to implement an inefficient and overly complicated solution just to conform to an arbitrary rule with which I do not agree.

    You try to tell me that my solution is wrong because it creates a dependency with my singleton, which simply shows that you do not undestand what the term “dependency” means. All of my classes can be instantiated either with or without my singleton, therefore there is no dependency. That’s the problem with so many OO “experts” today – they take a simple word and redefine what it means in order to make themselves look more intelligent than they really are.

  • Lars Olesen

    Nice article. Are you proposing that one uses this factory/container when creating all objects in an application?

  • http://www.assemblysys.com/dataServices/index.php mniessen

    @Tony:
    I see that you are still as passionate as ever about you coding style! ;) That’s what brought me to your site a few years ago.

    @everyone else
    I think that before dissing Tony’s programming or saying that he doesn’t write OO code,… you should take a look at his website, particularly the tutorial called “Using PHP Objects to access your Database Tables”. I know he also disses others’ ways of doing things, but he usually has good (better) arguments, at least IMHO.
    Does he program in an “original” way (as compared to the majority of programmers, bloggers or not)? Yes.
    Does he write in object-oriented style? Yes.
    Is he pissing lots of people by his rather direct comments? Absolutely, but it’s part of his charm. Well, not really… but who cares? We’re talking programming here, not popularity contest.

    My point is, you may or may not like the man because of his comments, but if you look at his way of doing things, I think you’ll have to admit his solution is really flexible and efficient.
    The mentionned article is from a few years back (before everyone got crazy, crazy about PHP frameworks) and it is still a very refreshing way of thinking.
    In it, Tony explains a great way to work with databases. I’m not saying it’s the best way of doing things in every single project, or that it is extremely easy to work with at first. But in my experience, since I’ve discovered it, everytime I failed to work that way –usually because it’s just a small and simple project that doesn’t require a lot of DB access, at some point I regretted it (when the project expands).

    Just my 2 cents.

    Michaël

  • honeymonster

    kyber said:

    It’s inherently difficult (impossible even) to do static code analysis on a dynamically typed language.

    Then you need to take a look at how Visual Studio 2008 handles JavaScript. I used to believe this would be too difficult, too (maybe it is, but obviously not impossible). As you type VS2008 does a pseudo-execution of the code ; presumably ignoring all side-effects such as output etc. but actually including other referenced javascript files. This enables “intellisense” and “code-completion”. Jaw-dropping the first time you encounter it, actually.

    I believe that I’ve seen a reference somewhere to another JavaScript IDE (predating VS2008) with a similar technology. This approach (pseudo-execution) should also be possible for PHP.

  • webaddictz

    Perhaps the vendors of these IDE’s should allow the user to hook in small scriptlets, to help determine the type.

    Both Zend Studio and Eclipse provide this hook by writing;
    /* @var ObjectType $object */

    Kyber, this is a great article.

  • blueyon

    I agree with Kyber on this.

    Using static singletons are bad news when developing large applications.

    One of my experiences from working on a large application that had been worked on by many other developers was that I did not know which singleton names where already in use.

    Another major problem was autoloading. How are you soposed to know what static sinlgeton are preloaded without having to register each class with zend loader. Thiongs get messy very quickly.

    If you use Kyber example you keep all your required instances in one nice factory class. You can also use magic methods to get the required classes. It also sticks with true OOP principles.

  • http://www.tonymarston.net Tony Marston

    blueyon: Using static singletons are bad news when developing large applications.

    me: That has not been my experience. My current application has 100′s of classes and 1000′s of tasks, and my static singleton has performed flawlessly for several years.

    blueyon: One of my experiences from working on a large application that had been worked on by many other developers was that I did not know which singleton names where already in use.

    me: That is not a problem for me. I have a separate singleton class, not a singleton method within each class, so there is no possibility of any confusion with names. What can be simpler than the following:

    $object & singleton::getInstance('classname');

    blueyon: Another major problem was autoloading.

    me: I don’t have any problems with autoloading as I never use it. I load classes when *I* want in a manner of *my* choosing, and refuse to rely on any automatic features within the language as experience has shown me that such features often work in peculiar and unexpected ways.

    blueyon: It also sticks with true OOP principles.

    me: Absolute rubbish. There is nothing in the principles of OO which says “Thou shalt not use globals under any circmstances” or “Thou shalt always employ the factory pattern”. You must be thinking of something you read on the wall in a men’s room somewhere.

  • http://www.tonymarston.net Tony Marston

    Whoops. That should be

    $object =& singleton::getInstance('classname');

  • Shrike

    It should be plainly obvious that a Singleton robs you of major benefits of object oriented programming, while giving you the (slight) benefit of easy access to classes (*not* objects). For example the Singleton object cannot be runtime polymorphic because you have referred directly to a classname rather than an object instance.

    It may suit your programming style Tony, but it is not object oriented in the least.

    -Paul

  • http://www.tonymarston.net Tony Marston

    Shrike: It should be plainly obvious that a Singleton robs you of major benefits of object oriented programming, while giving you the (slight) benefit of easy access to classes (*not* objects).

    me: Rubbish. The purpose of a singleton is to satisfy multiple requests for a class instance with references to a single shared instance instead of multiple instances. That’s where the term “single” in “singleton” comes from. The output of a singleton is an object, not a class.

    Shrike: the Singleton object cannot be runtime polymorphic because you have referred directly to a classname rather than an object instance.

    me: You are talking out of the wrong end of your alimentary canal. Polymorphism has nothing to do with class names, it is about method names. It allows the programmer to use the same method name on different objects, hence the description “same interface, different implementation”.

    Shrike: It may suit your programming style Tony, but it is not object oriented in the least.

    me: Your knowledge of polymorphism clearly demonstrates that it is YOU who does not know what OOP really means. You are obviously a graduate of the haven’t-a-clue academy.

  • Shrike

    Programming god Marston: Polymorphism has nothing to do with class names.

    Me: That’s precisely why referring to a classname is bad, you moron.

  • Shrike

    Kyber: sorry for going off track, great article as always.

  • http://www.tonymarston.net Tony Marston

    me: Polymorphism has nothing to do with class names.

    Shrike: That’s precisely why referring to a classname is bad, you moron.

    me: You are getting confused between the terms “singleton” and “polymorphism”. They are totally unrelated. I pass a class name to a singleton in order to obtain an instance of that class. I can use the same method names on different objects to achieve poymorphism. Singletons use class names while polymorhism uses method names. Now who’s a moron?

  • Shrike

    The whole frikkin’ point of polymorphism is that you are dealing with the same *object*, who’s type is determined at runtime. Are you trying to tell me that you would create two objects and then decide which one to use, and call that polymorphism?

  • http://www.tonymarston.net Tony Marston

    Polymorphism is *not* about dealing with the same object, it is about using the same method name on *different* objects.

  • blueyon

    Polymorphism is about extending a object and adding more functionality to it.

    It makes no differnce to use a real object and pass it around to objects that need it. You have to get used to how to pass the registry object around.

    Using static methods seems to be the easy way out and is not OOP. You might aswell just use a function.

  • http://www.tonymarston.net Tony Marston

    blueyon: Polymorphism is about extending a object and adding more functionality to it.

    me: No it isn’t. It’s about extending a base class to create subclasses, and hence different objects. This is “ad-hoc polymorphism”, as described in http://en.wikipedia.org/wiki/Polymorphism_(computer_science)

    In OOP, ad-hoc polymorphism is generally supported through object inheritance, i.e., objects of different types may be treated uniformly as members of a common superclass.

    blueyon: Using static methods seems to be the easy way out and is not OOP. You might as well just use a function.

    me: It does not matter the singleton is implemented as a class or a function, it is still a singleton. Just because it is simple does not make it “not OOP”. You seem to be one of these geeks who thinks that “proper” OOP has to be as complicated as possible, whereas I follow the KISS principle.

    What I do may not be to your taste, but it does not make it “not OOP”.

  • blueyon

    Tony: It’s about extending a base class to create subclasses

    Thats what I said!

  • http://www.tonymarston.net Tony Marston

    No, you said (and I quote):

    The whole frikkin’ point of polymorphism is that you are dealing with the same *object*,

    I am not dealing with the same object, I am dealing with multiple objects which just happen to inherit from the same superclass. That does *not* make them the same object.

  • blueyon

    You must be seeing things.

    This is what was said:

    Polymorphism is about extending a object and adding more functionality to it.

  • http://www.tonymarston.net Tony Marston

    You said (and I quote):

    the Singleton object cannot be runtime polymorphic because you have referred directly to a classname rather than an object instance.

    An object is not polymorphic, but an object’s methods can be. Polymorphism is about several objects sharing common method names. How those objects are instantiated, whether via a singleton or not, has absolutely nothing to do with polymorphism.

    I repeat, polymorphism and singletons are unrelated, are independent of each other, so for you to say that an object which is instantiated via a singleton cannot be polymorphic is completely wrong.

  • blueyon

    No I did not say that!

    Check the names above the post it was Shrike who said it!

  • http://www.tonymarston.net Tony Marston

    By arguing against my point of view you are effectively joining forces with everyone else who is arguing against my point of view. You said:

    Polymorphism is about extending a object and adding more functionality to it.

    That is wrong. Polymorphism is not about extending an object, it is about extending a superclass into a subclass from which a new object can be created.

  • blueyon

    This comment has been removed by the site administrator

  • http://www.tonymarston.net Tony Marston

    So what am I wrong about? Singletons? Polymorphism? The fact that the use of the word “dependency” is this article not correct?

    Your definition of polymorphism does not agree with the one at http://en.wikipedia.org/wiki/Polymorphism_(computer_science), so what makes you think that you are so right?

    Polymorphism is the ability to use the same methods on different objects, not about extending the same object.

    The use of a singleton has no effect on polymorphism.

    The use of a singleton does not constitute a dependency.