user105121
user105121

Reputation:

PHP 5.2 Virtual-like static methods

Here is my situation: I have a PHP base class that looks something like this:

class Table {
  static $table_name = "table";
  public function selectAllSQL(){
    return "SELECT * FROM " . self::$table_name;
  }
}

And a subclass that is like this:

class MyTable extends Table {
  static $table_name = "my_table";
}

Unfortunately, when I do:

MyTable::selectAllSQL()

I get:

"SELECT * FROM table"

instead of my desired result,

"SELECT * FROM my_table"

It looks like this can be accomplished in php 5.3 using late static bindings, but is there any way I can accomplish this behavior in PHP 5.2.x?

Upvotes: 4

Views: 2380

Answers (4)

Matt
Matt

Reputation: 1143

Yeh late static binding is the way to go. Maybe you are on PHP 5.3 by now. Here is how it should look then:

Change

class Table {
  static $table_name = "table";
  public function selectAllSQL(){
    return "SELECT * FROM " . self::$table_name;
  }
}

to

class Table {
  static $table_name = "table";
  public function selectAllSQL(){
    return "SELECT * FROM " . static::$table_name;
  }
}

Upvotes: 2

eisberg
eisberg

Reputation: 3771

Instantiate the class of cause is an option!

<?php
abstract class Table {
    protected $table_name;
    public function selectAllSQL() {
        return 'SELECT * FROM ' . $this->table_name;
    }
}

class MyTable extends Table {
    protected $table_name = 'my_table';
}

$my_table = new MyTable();
echo $my_table->selectAllSQL(); // Will output "SELECT * FROM my_table"

If you have to keep static than reimplementation is the only way to go in PHP < 5.3:

<?php
abstract class Table {
    protected static $table_name = 'table';
    public static function selectAllSQL() {
        return self::selectAllSQLTable(self::$table_name);
    }
    public static function selectAllSQLTable($table) {
        return 'SELECT * FROM ' . $table;
    }
}

class MyTable extends Table {
    protected static $table_name = 'my_table';
    public static function selectAllSQL() {
        return self::selectAllSQLTable(self::$table_name);
    }
}

class MyOtherTable extends Table {
    protected static $table_name = 'my_other_table';
    public static function selectAllSQL() {
        return self::selectAllSQLTable(self::$table_name);
    }
}

echo MyTable::selectAllSQL(); // Will output "SELECT * FROM my_table"
echo MyOtherTable::selectAllSQL(); // Will output "SELECT * FROM my_other_table"

Upvotes: 1

Edward Z. Yang
Edward Z. Yang

Reputation: 26762

Not really. That's why LSB was added to 5.3. Instantiation is the way to go, in this place, along with a singleton.

Upvotes: 3

Evert
Evert

Reputation: 99816

Would it be an option to instantiate the classes?

Upvotes: 0

Related Questions