how do you create an enumeration. i have this but i get a T_STRING error

enum DB{a,b}

    You mean as a database type? like
    choice ENUM("Yes","No","Maybe")

      no im not connecting to a database.

      i just want to enumerate values in php.

        To enumerate means to either list or count something so are you wanting to maybe count() the values of an array?

          no im not connecting to a database.

          i just want to enumerate values in php.

            Houdini wrote:

            To enumerate means to either list or count something so are you wanting to maybe count() the values of an array?

            no.

            if i want a variable that has a limited number of possible choices I can enumerate it.

            Its just like the first person that commented on this thread. The SQL way to enumerate a field is ENUM("yes","No","Maybe")

            That feild can only have yes,no,or maybe as possible choices

            my assumption was to use this

            enum DB
            {
            a,b,c,d,e,f
            };

              There is no enum PHP function but you can with php count the values contained in an array with count() like so.

              <?php
              $a[0] = 1;
              $a[1] = 3;
              $a[2] = 5;
              echo $result = count($a)."<br />";//this will print 3
              // $result == 3
              ?>

              To learn more there is also array_count_values() and list() and you can find out more in the Arrays section of PHP:Manual count()

                8 days later

                Houdini, you obviously don't know what an enum is.
                But you are right with one thing there is not language feature for enums. Its one of the things I miss from C++.

                Does anybody know of a class that has implemented enumish behaviour?

                  Not surprising, since C++ is strongly-typed and PHP is loosely-typed, just as C++ is an object-oriented language and PHP isn't. They're two different beasts.

                    after looking at the enum for C++ I found that the closest thing you can come to it in PHP is the array() function in your example enum DB('a','b','c','d') would be

                    $DB= array('a','b','c','d');
                    print_r($DB);//would output
                    Array
                    (
                        [0] => a
                        [1] => b
                        [2] => c
                        [3] => d
                    )
                    echo $DB[0];//would output
                    a
                    
                      2 years later

                      We can completely recreate this with arrays cant we?

                      <?
                      class enum {
                      
                         var $enum_array;
                      
                         function enum(){
                      
                        $this->enum_array = array();
                      
                         }
                      
                      
                         function addEnum($key, $val){
                            $this->enum_array[$key] = $val;
                         }
                      
                      
                         function getEnum($value){
                      
                        if(key_exists($value, $this->enum_array)){
                           return $this->enum_array[$value];
                        }
                        if(($enum_value = array_search($value, $this->enum_array))){
                           return $this->enum_array[$enum_value];
                        }
                      
                        return false;
                         }
                      
                      }
                      
                      //say our enumeration is for keeping track of how many points a space ship in a game is worth
                      $point_value = new enum();
                      
                      $point_value->addEnum('SHIP1', 10);
                      $point_value->addEnum('SHIP2', 20);
                      $point_value->addEnum('SHIP3', 40);
                      $point_value->addEnum('SHIP4', 100);
                      
                      
                      echo $point_value->getEnum(100);
                      echo "<br/>";
                      echo $point_value->getEnum('SHIP1');
                      
                      //returns false becausee we don't have this key
                      echo $point_value->getEnum('1000');
                      //returns false because this is not a value of a key
                      echo $point_value->getEnum('SHIP99');
                      
                      ?>
                      

                      Does this give the desired effect?

                      -- edit --
                      Sorry, my server is still stuck in php4 so my examples suffer the same fate.

                        5 months later

                        Would using a Class with Static Properties work? Like this:

                        class AuthStatus {
                            public static $None = '0';
                            public static $Accepted = '1';
                            public static $Rejected = '2';
                            public static $Pending = '3';
                        }
                        
                        class Auth {
                            public $status;
                        
                        function __construct() {
                            $this->EnsureAuthStatus ();
                        }
                        
                        private function EnsureAuthStatus() {
                            if (! $this->status) {
                                $this->status = AuthStatus::$None;
                            }
                        }
                        
                        public function DisplayAuthStatus() {
                            switch ($this->status) {
                                case AuthStatus::$None :
                                    return "None";
                                    break;
                                case AuthStatus::$Accepted :
                                    return "Accepted";
                                    break;
                                case AuthStatus::$Pending :
                                    return "Pending";
                                    break;
                                case AuthStatus::$Rejected :
                                    return "Rejected";
                                    break;
                                default:
                                    return "Default";
                                    break; 
                            }
                        }
                        }
                          ichc.scott;10901559 wrote:

                          Would using a Class with Static Properties work?...

                          I don't think I like that, since the public static properties could be easily overwritten by the client code, affecting every instance of that class.

                          For a general-purpose enum class I might do something like:

                          <?php
                          /**
                           * A generic enumeration object
                           **/
                          class Enum
                          {
                             /**
                              * @var array Allowed values
                              **/
                             protected $values = array();
                          
                             /**
                              * @var mixed Current value
                              **/
                             protected $value;
                          
                             /**
                              * Constructor
                              * @return void
                              * @param array $values
                              **/
                             public function __construct($values, $value = null)
                             {
                                if(is_array($values) and count($values))
                                {
                                   foreach($values as $val)
                                   {
                                      $this->values[] = $val; // make sure we have enumerated array
                                   }
                                   $this->value = $value;
                                }
                                else
                                {
                                   throw new Exception("Constructor param must be a non-empty array");
                                }
                             }
                          
                             /**
                              * Get current value
                              * @return mixed
                              * @param string $value 'value'
                              **/
                             public function __get($value)
                             {
                                if(strtolower($value) === 'value')
                                {
                                   return $this->value;
                                }
                                else
                                {
                                   throw new Exception("Invalid arg '$value'");
                                }
                             }
                          
                             /**
                              * Set current value
                              * Throws exception on invalid value
                              * @return bool
                              * @param string $key 'value'
                              * @param mixed $value
                              **/
                             public function __set($key, $value)
                             {
                                if(strtolower($key) === 'value')
                                {
                                   if(in_array($value, $this->values))
                                   {
                                      $this->value = $value;
                                      return true;
                                   }
                                   elseif(is_null($value))
                                   {
                                      $this->value = $this->values[0];
                                   }
                                   else
                                   {
                                      throw new Exception("'$value' not a valid enum value");
                                   }
                                }
                                else
                                {
                                   throw new Exception("Invalid key '$key'");
                                }
                             }
                          }
                          
                          ///////////////
                          // SAMPLE USAGE
                          ///////////////
                          try
                          {
                             $fruits = new Enum(array('apple', 'orange', 'banana'));
                             echo $fruits->value . "<br>\n"; // apple
                             $fruits->value = 'orange';
                             echo $fruits->value; // orange
                             $fruits->value = 'grape'; // exception
                          }
                          catch(Exception $e)
                          {
                             echo "<pre>".print_r($e, 1)."</p>";
                          }
                          

                          If you want to hard-wire such a class to a specific set of values, then you could extend the Enum class and define the $values array directly within the class definition and remove that arg from the constructor:

                          class ColorEnum extends Enum
                          {
                             protected $values = array(
                                'red',
                                'blue',
                                'yellow'
                             );
                          
                             public function __construct($value=null)
                             {
                                $this->value = $value;
                             }
                          }
                          
                            8 months later

                            wow NogDog, that's awesome. I've found lack of enums in php really frustrating.

                            In your subclass's constructor though it should be "$this->set('value',$value);" because "set" won't be called on "$this->value = $value." So that users wouldn't forget, I'd probably write it in a way that the base-class constructor generated objects.

                            I think I'd also want the ColorEnum class to be final to prevent a subclass from adding new entries, and I'd probably just go ahead and make the base class abstract.

                            pretty cool though, I've seen many enum attempts on various php sites; this is the best I've seen.

                              Interesting thread resurrection, so I shall contribute my two cents...

                              gir wrote:

                              Does anybody know of a class that has implemented enumish behaviour?

                              We should define "enumish behaviour". One could define a general enumeration concept of a user defined type with a fixed number of possible values. This appears to be what kelphis was asking for in post #6.

                              An enumeration in C and C++ is a fixed list of named integral compile-time constants such that if no value is explicitly assigned to an enumerator, its value is one greater than the previous enumerator's value, and if the first enumerator is not explicitly assigned a value, its value is zero. An enumeration definition defines a type (but in C there is no safety provided at all against assigning a value to an object of an enum type such that the value is outside of the list of enumerator values). kelphis' examples in posts #1 and #6 appear to be of this kind.

                              Protato's suggestion seems more along the lines of a C and C++ enumeration, except that it is extensible at run time, is not restricted to integer values, and each enumeration is just an object rather than a type. We could make the addEnum() method's second parameter optional in order to emulate the lack of an explicit value assignment (and restrict the values to integers). On the other hand, creating an enumeration is more cumbersome than in C and C++, and accessing an enumerator looks very much like the method call that it is rather than the accessing of a named constant. Since the enumeration is not a type, one cannot create objects of a particular enumeration type, so the use case of this enum class seems to be restricted as a list of immutable name/value pairs.

                              I think that by using [man]array_flip/man, one could take advantage that keys in an array in PHP can be defined much like how enumerator values are defined in C and C++ enumerations, and thus allow for a less cumbersome way of creating an enumeration. Overloading __get would allow for a more desirable syntax.

                              NogDog's solution seems more along the lines of the more general enumeration concept. Through inheritance, one can create enumeration types. One drawback though is that each enumeration object will have its own array of values, despite this array being identical across all objects of its (sub)type. However, the PHP interpreter might be smart enough to recognise this and apply an appropriate optimisation (copy on write?), especially considering that the initialisation is performed as part of the variable declaration.

                                12 years later
                                Write a Reply...