views:

2683

answers:

7

Lately I've been in the habit of assigning integer values to constants and simply using the constant name as a means of identifying its purpose. However, in some cases this has resulted in the need to write a function like typeToString($const) when a string representation is needed. Obviously this is inefficient and unneccesary, but is only an issue every once and a while.

So my question is, are there any other tradeoffs I should consider? Which case is considered to be cleaner/more standards-compliant? Also, is the performance difference negligable for most cases?

Case 1: (faster when a string version is not needed?)

class Foo {
    const USER_TYPE_ADMIN = 0;
    const USER_TYPE_USER = 1;
    const USER_TYPE_GUEST = 2;

    public $userType = self::USER_TYPE_ADMIN;

    public function __construct($type) {
     $this->userType = $type;
    }

    public function typeToString() {
     switch($this->userType) {
      case self::USER_TYPE_ADMIN:
       return 'admin';
       break;

      case self::USER_TYPE_USER:
       return 'user';
       break;

      case self::USER_TYPE_GUEST:
       return 'guest';
       break;

      default:
       return 'unknown';
       break;
     }
    }
}

$foo = new Foo(Foo::USER_TYPE_GUEST);
echo $foo->typeToString();
// Displays "guest"

Case 2:(faster/easier when a string version is needed)

class Foo {
    const USER_TYPE_ADMIN = 'admin';
    const USER_TYPE_USER = 'user';
    const USER_TYPE_GUEST = 'guest';

    public $userType = self::USER_TYPE_ADMIN;

    public function __construct($type) {
     $this->userType = $type;
    }
}

$foo = new Foo(Foo::USER_TYPE_GUEST);
echo $foo->userType();
// Displays "guest"
A: 

Instead of using const integers I generally just go with strings if I need to print them. So I'd do something like $foo = new Foo('guest');. I can still validate the input in the constructor and I can mark it up whenever I need it.

Jasper Bekkers
This is what I'd do too, but the OP seems to have come from a stricter background... maybe an ex C++ or Java programmer :p
Greg
I'm currently a C++ developer and even uses strings there in the general case.
Jasper Bekkers
+3  A: 

I'll be honest, I don't know if there's a performance "hit" of any kind when you define your constants natively as strings - but if there is one at all I'm willing to bet that it's so small it would be difficult to measure.

Personally, if the constant's value is meaningful as a literal, then just assign it that value. If the constant's value is meaningful only as an option selector (or some other indication of value), then use integers or whatever you choose appropriate.

Peter Bailey
Comparing strings is more expensive than comparing integers.
phjr
But the difference between 10 string comparisons and 10 integer comparisons is so tiny that if it makes coding easier, it's better to use strings
Greg
Ya phjr, but using integers when you really want strings just to shave milliseconds of milliseconds off each request just absolutely REEKS of pre-optimization.
Peter Bailey
A: 

I think string constants are the best choice in this case. Code looks better.

Of course if you need last bit of performance, use integer constants. But only after you verify with a profiler that string comparisons are the bottleneck. Anyway, in most applications there are many more expensive things, like database access etc.

phjr
+8  A: 

The performance difference will be negligible unless you're storing a lot of them. I'd probably write the toString a little more concisely:

$strings = array
(
    self::USER_TYPE_ADMIN => 'admin',
    self::USER_TYPE_USER => 'user',
);

if (!isset($strings[$type]))
    return 'unknown';

return $strings[$type];

You could make $strings static.

Greg
A: 

Blah blah premature optimization.

eyelidlessness
In otherwords:Rules for optimisation.1) Don't optimise. 2) (For experts only). Don't optimise yet.
Alya
A: 

In the example you write you could drop all the methods and make the class static and you would have created your self an Enumerator. Like this:

class Enumeration{
  public static const One=1;
  public static const Two=2;
  public static const Three=3;
}

One other handy way to use constants is to use them as application configuration. They are much faster performance wise then parsing an xml file for configuration.

Nikola Stjelja
A: 

Nikola, php does not allow "public static" keywords for constants. Your code will generate a syntax error.

Anand