Dynamic Classes

31 07 2010

There is a little bit of a mystery involving dynamic class creation. Suppose I were to write a snippet which seeks to instantiate class bar residing in namespace some\ns as follows:

if ($choice == 1) {
		$obj = new "some\\ns\\bar";

I escape the backslash so that, the parser avoids mistaking it’s presence before another character as a special sequence representing a non-printable character. Given that the string has a backslash before the letter n, the parser would mistake that for a newline so I escape the backslash. I also escape the backslash before the letter b, just in case the parser were to interpret it too as a non-printable character.

You could  write the code using single quotes as ‘some\ns\bar’ and that would save you from having to escape the backslashes. However, whether double or single quoted, the parser generates an error message, complaining about an unexpected token constant encapulated string (T_CONSTANT_ENCAPSED_STRING) in PHP5.3.1. Yet the online manual shows such examples as being feasible! (See www.php.net/manual/en/language.namespaces.faq.php#language.namespaces.faq.quote, Example #9.)

I suspect that the manual’s example is incorrect. The error message itself hints that  new needs to be followed by a constant value , not a string literal or in other words, a quoted string.

You might think that we could remedy the situation by defining a constant as follows:

define("cname", "some\\ns\bar");
$obj = new cname;

This fails to ameliorate the situation. Instead, a new parser error emerges, complaining that it is unable to find a class entitled cname. Recall that new is responsible for instantiating a class based on the classname provided (see http://www.java-samples.com/showtutorial.php?tutorialid=911).

The solution for dynamically creating an object is simple.  Assign a class’s name to a variable and then use that variable preceded by the keyword new. After new, PHP expects a classname that “starts with a letter or underscore, followed by any number of letters, numbers, or underscores.” (See http://www.php.net/manual/en/language.oop5.basic.php.)

But isn’t a variable containing a string value a quoted string? Surprisingly, far from it.  If I wished to have a quoted string, then I’d have to write code enclosing the string with an additional pair of quotes, like the following:

$name = ' "some\\ns\\bar" ';
echo $name;

We use quotes to denote that a variable contains a string value but the quotes themselves are not part of that value unless you add an extra pair of them.

Clearly, whether we use double or single quoted strings, both will fail when used with new; valid classnames do not contain quote characters! So, we can revise the code to work properly, as follows:

if ($choice == 1) {
     $classname = "some\\ns\\bar";
     $obj = new $classname;

This work is licensed under a Creative Commons License



Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

%d bloggers like this: