Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Dynamically populating a static variable in PHP

Tags:

object

php

static

I have two static values: "type" and "typeID". Type is human readable and constant, and typeID needs to be looked up from the database, based on the value of type. I need the lookup to happen once, when the class definition is first loaded

To illustrate, here is some code that doesn't work because you can't call functions in the declaration space.

MyClass extends BaseClass {
  protected static $type = "communities";
  protected static $typeID = MyClass::lookupTypeID(self::$type);
}

Is there a magic method that is called exactly once when the class definition is loaded? If there is something obvious I'm missing it.

like image 499
slifty Avatar asked May 16 '11 22:05

slifty


2 Answers

shamelessly pulled from the php manual's static keyword comments:

Because php does not have a static constructor and you may want to initialize static class vars, there is one easy way, just call your own function directly after the class definition.

for example.

<?php
function Demonstration()
{
    return 'This is the result of demonstration()';
}

class MyStaticClass
{
    //public static $MyStaticVar = Demonstration(); //!!! FAILS: syntax error
    public static $MyStaticVar = null;

    public static function MyStaticInit()
    {
        //this is the static constructor
        //because in a function, everything is allowed, including initializing using other functions

        self::$MyStaticVar = Demonstration();
    }
} MyStaticClass::MyStaticInit(); //Call the static constructor

echo MyStaticClass::$MyStaticVar;
//This is the result of demonstration()
?>
like image 92
nathan gonzalez Avatar answered Nov 07 '22 17:11

nathan gonzalez


Simple and no magic needed, don't forget you can always define a variable as null and test that it is null (doing the db call only then). Then it's just a matter if you want that to happen when the class is constructed or included (include_once etc...)

MyClass extends BaseClass {
    protected static $type = "communities";
    protected static $typeID = null;

    public function __construct(){
        if(is_null(self::$typeID)){
            self::lookupTypeID(self::$type);
        }
    }

    public static lookupTypeID($type){
        self::$typeID = //result of database query
    }
}

or

MyClass::lookupTypeID(); //call static function when class file is included (global space)

MyClass extends BaseClass {
    protected static $type = "communities";
    protected static $typeID = null;

    public function __construct(){

    }

    public static lookupTypeID($type=null){
        if(is_null($type)){
            $type = self::$type;
        }
        self::$typeID = //result of database query (SELECT somefield FROM sometable WHERE type=$type) etc..
    }
}

a static constructor is more like a factory method

if(!function_exists(build_myclass)){
    function build_myclass(){
        return MyClass::build();
    }
}

MyClass extends BaseClass {
    protected static $type = "communities";
    protected static $typeID = null;

    public function __construct(){

    }

    public static function build(){
        return new self(); //goes to __construct();
    }

 }

$class = new MyClass(); //or
$class = MyClass::build(); //or
$class = build_myclass();
like image 33
user2272605 Avatar answered Nov 07 '22 19:11

user2272605