title: Best workaround to create a PHP class constant from an expression?
body: <p>I'd like to be able to do something like this:</p>
  
  <pre class="lang-php prettyprint-override"><code>class Circle {
  
      const RADIUS_TO_CIRCUMFERENCE = M_PI * 2;  // Not allowed
  
      private $radius;
  
      public function __construct( $radius ) {
          $this-&gt;radius = $radius;
      }
  
      ...
  
      public function getCircumference() {
          return $this-&gt;radius * self::RADIUS_TO_CIRCUMFERENCE;
      }
  
  }
  </code></pre>
  
  <p>But I can't create a <a href="http://php.net/manual/en/language.oop5.constants.php" rel="noreferrer">class constant</a> from an expression like that:</p>
  
  <blockquote>
    <p>The value must be a constant expression, not (for example) a variable, a property, a result of a mathematical operation, or a function call.</p>
  </blockquote>
  
  <p><br/>
  So my question is: What's the best workaround for this limitation of PHP?  I'm aware of the following workarounds, but are there any others which are better?
  <br/><br/></p>
  
  <h2>1. Create a property</h2>
  
  <pre class="lang-php prettyprint-override"><code>class Circle {
  
      private static $RADIUS_TO_CIRCUMFERENCE;
  
      private $radius;
  
      public function __construct( $radius ) {
          $this-&gt;radius = $radius;
          $this-&gt;RADIUS_TO_CIRCUMFERENCE = M_PI * 2;
      }
  
      ...
  
      public function getCircumference() {
          return $this-&gt;radius * $this-&gt;RADIUS_TO_CIRCUMFERENCE;
      }
  
  }
  </code></pre>
  
  <p>I don't like this, because the value of <code>$RADIUS_TO_CIRCUMFERENCE</code> can be changed, so it's not really a "constant".
  <br/><br/></p>
  
  <h2>2. Use <code>define()</code></h2>
  
  <pre class="lang-php prettyprint-override"><code>define( 'RAD_TO_CIRCUM', M_PI * 2 );
  
  class Circle {
  
      const RADIUS_TO_CIRCUMFERENCE = RAD_TO_CIRCUM;
  
      ...
  
      public function getCircumference() {
          return $this-&gt;radius * self::RADIUS_TO_CIRCUMFERENCE;
      }
  
  }
  </code></pre>
  
  <p>This is better, since the value is truly constant, but the drawback is that <code>RAD_TO_CIRCUM</code> has been globally defined.</p>
  
  <p><strong>A digression</strong></p>
  
  <p>I don't understand how this can work. <em>(Edit: I've tested it, and it does work.)</em> According to the <a href="http://www.pvtuts.com/php/php-static#const-define" rel="noreferrer">Handbook of PHP Syntax</a>:</p>
  
  <blockquote>
    <p>The <code>const</code> modifier creates a compile-time constant and so the compiler will replace all usage of the constant with its value. In contrast, <code>define</code> creates a run-time constant which is not set until run-time. This is the reason why <code>define</code> constants may be assigned with expressional values, whereas <code>const</code> requires constant values which are known at compile-time.</p>
  </blockquote>
  
  <p>The manual <a href="http://php.net/manual/en/language.constants.syntax.php" rel="noreferrer">confirms</a> that "constants defined using the <code>const</code> keyword ... are defined at compile-time".</p>
  
  <p>In <a href="https://bugs.php.net/bug.php?id=51765" rel="noreferrer">this bug report</a> from 3 years ago, a member of the PHP team wrote:</p>
  
  <blockquote>
    <p>For the class constant we need a constant value at compile time and can't evaluate expressions. <code>define()</code> is a regular function, evaluated at run time and can therefore contain any value of any form.</p>
  </blockquote>
  
  <p>But in my example above, the value of <code>RAD_TO_CIRCUM</code> is not known at compile-time. So what is the compiler putting for the value of <code>RADIUS_TO_CIRCUMFERENCE</code>?</p>
  
  <p>I'm guessing that the compiler creates some kind of placeholder for the value of <code>RADIUS_TO_CIRCUMFERENCE</code>, and at run-time, that placeholder gets replaced with the value of <code>RAD_TO_CIRCUM</code>. Might this placeholder be a kind of <a href="http://php.net/manual/en/language.types.resource.php" rel="noreferrer">resource</a>? If so, maybe this technique should be avoided? The manual <a href="http://php.net/manual/en/language.constants.syntax.php" rel="noreferrer">says</a>: "It is possible to define constants as a resource, but it should be avoided, as it can cause unexpected results."
  <br/><br/></p>
  
  <h2>3. Create a method</h2>
  
  <pre class="lang-php prettyprint-override"><code>class Circle {
  
      ...
  
      private static function RADIUS_TO_CIRCUMFERENCE() {
          return M_PI * 2;
      }
  
      public function getCircumference() {
          return $this-&gt;radius * $this-&gt;RADIUS_TO_CIRCUMFERENCE();
      }
  
  }
  </code></pre>
  
  <p>This is my favourite workaround that I'm aware of. The value is constant, and it doesn't affect the global space.</p>
  
  <p>Is there another workaround which is even better?</p>