tags:

views:

601

answers:

6
+6  Q: 

define() vs const

Pretty straightforward question: In PHP, do you prefer to do (and why):

define('FOO', 1);

OR

const FOO = 1;

Also, the code is NOT in a class.

Thanks.

+10  A: 

define i use for global constants.

const i use for class constants.

You cannot define into class scope, and with const you can. Needless to say, you cannot use const outside class scope

Also, with const, it actually becomes a member of the class, with define, it will be pushed to global scope.

Jacob Relkin
+1  A: 

define is general purpose and const can be used in classes.

Sarfraz
+9  A: 

const can't be used in the global scope. You can only use this from within a class. This should be used when you want to set some kind of constant option or setting that pertains to that class. Or maybe you want to create some kind of enum.

define can be used for the same purpose, but it can only be used in the global scope. It should only be used for global settings that affect the entire application.

An example of good const usage is to get rid of magic numbers. Take a look at PDO's constants. When you need to specify a fetch type, you would type PDO::FETCH_ASSOC, for example. If consts were not used, you'd end up typing something like 35 (or whatever FETCH_ASSOC is defined as). This makes no sense to the reader.

An example of good define usage is maybe specifying your application's root path or a library's version number.

ryeguy
It might be worth mentioning the use of `const` with namespaces.
salathe
+2  A: 

I believe that as of PHP 5.3, you can use const outside of classes, as shown here in the second example:

http://www.php.net/manual/en/language.constants.syntax.php

<?php
// Works as of PHP 5.3.0
const CONSTANT = 'Hello World';

echo CONSTANT;
?>
mattle
+1  A: 

It seems to me, that the question was misunderstood. As of PHP 5.3 one may define constants outside classes using the class keyword, too.

So I'm going to describe when and why i use const instead of define().

First of all, one has to know a major difference between those two: const can only take scalar, non-expression values, i.e. strings, numbers and other constants (e.g. 1, "a", __FILE__, true, false, null).

That's why const BIT_XXX = 1 << 5; is not possible, whereas one can write define('BIT_XXX', 1 << 5);

So, always if I require some expression as constant value I am forced to use define().

Now, if one knows this difference I think a great advantage of const is obvious: const may be resolved at compile time, not at runtime (I think it is, but i dunno.) This results in a great performance advantage.

As most PHP developers know define() is notoriously slow - this is why people invented apc_load_constants() and hidef.

const does solve this problem,as one can see with some benchmarking:

First I defined all letters of the alphabet using const and then using define() and measured the time (all constants were assigned the value 1).

const: 7E-5 (compare to simply measuring time, without letting PHP do anything: 4E-5) define: 8E-4

So, const is more than 10 times faster than define()!

After that, I tested constant lookup, using this code (once with the constants defined using const, once using define()):

for ($i = 0; $i < 100000; ++$i) {
    a;b;c;d;e;f;g;h;i;j;k;l;m;n;o;p;q;r;s;t;u;v;w;x;y;z;
}

const: 0.8s define: 1.0s

Here the difference is by far not that large, but still, const is faster ;)

Now, for those not willing to read all this stuff: Use const as must as you can, because it's faster, shorter and is nicer to read! Only use define(), if you really do need dynamic constants names and values!

nikic
A: 

Yes, const are defined at compile-time and as nikic states cannot be assigned an expression, as define()'s can. But also const's cannot be conditionally declared (for the same reason). ie. You cannot do this:

if (/* some condition */) {
  const WHIZZ = true;  // CANNOT DO THIS!
}

Whereas you could with a define(). So, it doesn't really come down to personal preference, there is a correct and a wrong way to use both.

As an aside... I would like to see some kind of class const that can be assigned an expression, a sort of define() that can be isolated to classes?

w3d