Delicious Bookmark this on Delicious Share on Facebook SlashdotSlashdot It! Digg! Digg



PHP : Function Reference : Class/Object Functions : get_class

get_class

Returns the name of the class of an object (PHP 4, PHP 5)
string get_class ( [object object] )

Example 377. Using get_class()

<?php

class foo {
   function
foo()
   {
   
// implements some logic
   
}

   function
name()
   {
       echo
"My name is " , get_class($this) , "\n";
   }
}

// create an object
$bar = new foo();

// external call
echo "Its name is " , get_class($bar) , "\n";

// internal call
$bar->name();

?>

The above example will output:

Its name is foo
My name is foo

Related Examples ( Source code ) » get_class







Code Examples / Notes » get_class

mightye

To: Bryan
In this model it is still workable if your singleton variable is actually an array.  Consider:
<?php
abstract class Singleton {
   protected final static $instances = array();
   
   protected __construct(){}
   
   protected function getInstance() {
       $class = get_real_class(); // imaginary function returning the final class name, not the class the code executes from
       if (!isset(self::$instances[$class])) {
           self::$instances[$class] = new $class();
       }
       return self::$instances[$class];
   }
}
class A extends Singleton {
}
class B extends Singleton {
}
$a = A::getInstance();
$b = B::getInstance();
echo "\$a is a " . get_class($a) . "<br />";
echo "\$b is a " . get_class($b) . "<br />";
?>
This would output:
$a is a A
$b is a B
The only alternative as described elsewhere is to make getInstance() protected abstract, accept the class name as an argument, and extend this call with a public final method for every sub-class which uses get_class() in its local object scope and passes it to the superclass.
Or else create a singleton factory like this:
<?php
final class SingletonFactory {
   protected static $instances = array();
   
   protected getInstance($class) {
       if (!isset(self::$instances[$class])) {
           self::$instances[$class] = new $class();
       }
       return self::$instances[$class];
   }
}
?>
The downside to this of course to this latter model is that the class itself doesn't get to decide if it is a singleton, the calling code gets to decide this instead, and a class that really wants or *needs* to be a singleton has no way to enforce this, not even by making its constructor protected.
Basically these design patterns, and various other meta manipulations (things which operate on the nature of the object, not on the data the object holds) could benefit greatly from knowing exactly what the final type of this object is, and not having native access to this information obligates work-arounds.


janci

To yicheng zero-four at gmail dot com: Another, maybe better example where finding out the real class (not the class we are in) in static method should be quite usefull is the Singleton pattern.
There is currently no way how to create an abstract Singleton class that could be used just by extending it without the need to change the extended class. Consider this example:
<?php
abstract class Singleton
{
protected static $__instance = false;

public static function getInstance()
{
if (self::$__instance == false)
{
// This acctually is not what we want, $class will always be 'Singleton' :(
$class = get_class();
self::$__instance = new $class();
}
return self::$__instance;
}
}
class Foo extends Singleton
{
// ...
}
$single_foo = Foo::getInstance();
?>
This piece of code will result in a fatal error saying: Cannot instantiate abstract class Singleton in ... on line 11
The best way I figured out how to avoid this requires simple but still a change of the extended (Foo) class:
<?php
abstract class Singleton
{
protected static $__instance = false;

protected static function getInstance($class)
{
if (self::$__instance == false)
{
if (class_exists($class))
{
self::$__instance = new $class();
}
else
{
throw new Exception('Cannot instantiate undefined class [' . $class . ']', 1);
}
}
return self::$__instance;
}
}
class Foo extends Singleton
{
// You have to overload the getInstance method in each extended class:
public static function getInstance()
{
return parent::getInstance(get_class());
}
}
$single_foo = Foo::getInstance();
?>
This is of course nothing horrible, you will propably need to change something in the extended class anyway (at least the constructor access), but still... it is just not as nice as it possibly could be ;)


yicheng zero-four

To matsgefvert dot se and Marc,
I'm sorry but I'm still having a very difficult time understanding why you would want this behavior.  I understand that you are generating some code for some persistent layer for database access.  
In your code example, Marc, you say that you would like the SomeTable::read() to return "SomeTable" when called from your client.  Yet, at this point you *know* what the class name is.  Even assuming you are generating this code automatically, you can simply generate your SomeTable class as such.
<?php
class PersistedObject {
 //...
 public static function read($table, $key){
   // do some databasey stuff
   // with $table which is the table name
   return $table;
 }
}
class SomeTable extends PersistedObject {
 //...
 // make a copy in the child class
 public static function read($key){
   $table = get_class();
   return parent::read($table, $key);
 }
}
// this will now return "SomeTable"
$someTableObject = SomeTable::read(1234);
?>
I'm still failing to see how this would provide but a convenience for very rare & specific issues, at the cost of non-OOP behavior by allowing static methods to bind to objects instead of classes.  
One of the most common uses for get_class() is for debugging lines, for example:
<?php
class PersistedObject {
 //...
 public static function transaction($params){
   // do some stuff
   if ($error_occurred){
     echo "Error : WTFBBQ happened in " . get_class() . "::" . __FUNCTION__ . ".  Time to get some coffee!";
 }
}
class SomeTable extends PersistedObject {
 //...
}
SomeTable::transaction( $someParams );
?>
Now, when an error occurs inside the call to SomeTable::transaction(), we get incorrect error output.


luke

This note is a response to the earlier post by davidc at php dot net. Unfortunately, the solution posted for getting the class name from a static method does not work with inherited classes.
Observe the following:
<?php
class BooBoof {
 public static function getclass() {
   return __CLASS__;
 }
 public function retrieve_class() {
   return get_class($this);
 }
}
class CooCoof extends BooBoof {
}
echo CooCoof::getclass();
// outputs BooBoof
$coocoof = new CooCoof;
echo $coocoof->retrieve_class();
// outputs CooCoof
?>
__CLASS__ and get_class($this) do not work the same way with inherited classes. I have been thus far unable to determine a reliable way to get the actual class from a static method.


dan

This function does return the class name in lowercase, but that does not seem to make any difference. The code below, although very sloppy, works fine in all of the following configurations.
PHP 4.2.2 on Windows NT5 with Apache 1.3.24
PHP 4.2.1 in Zend Development Environment on box above
PHP 4.2.3 on Linux RedHat 7.3 with Apache 1.3.27
class TeSt {
  var $a;
  var $b = "Fred";
  // Notice the case difference in the constructor name
  function Test() {
     $classname = get_class($this); // $classname = "test"
     $this->ra = get_class_vars($classname);
  }
}
// Next line also works with Test(), TEST(), or test()
$obj = new TeSt();
print_r($obj->ra);
Result :
  Array
  (
      [a] =>
      [b] => Fred
  )


oliver dot pliquett @mediagear dot de

This function can become _VERY_ helpful if you want to return a new object of the same type. See this example:
<?php
class Foo{
var $name;

function Foo( $parameter ){
$this->name = $parameter;
}
function whoami() {
echo "I'm a " . get_class( $this ) ."\n";
}

function getNew() {
$className = get_class( $this );

// here it happens:
return new $className ( "world" ) ;
}
}
class Bar extends Foo {
function Bar( $name ){
$this->Foo( $name );
}
function welcome() {
echo "Hello, " . $this->name .  "! \n";
}
}
// We generate a Bar object:
$myBar = new Bar( "Oliver" );
$myBar->welcome();
//now let's instanciate a new Bar object.
//note: this method is inherited from Foo by Bar!
$baba = $myBar->getNew();
$baba->welcome();
$baba->whoami();
/* Output:
Hello, Oliver!
Hello, world!
I'm a bar
*/
?>


brjann

This behavior is unexpected, but good to be aware of
class parentclass {
public function getClass(){
echo get_class($this); //using "$this"
}
}
class child extends parentclass {
}
$obj = new child();
$obj->getClass(); //outputs "child"
class parentclass {
public function getClass(){
echo get_class(); //note, no "$this"
}
}
class child extends parentclass {
}
$obj = new child();
$obj->getClass(); //outputs "parentclass"


yicheng zero-four

This a response to luke at liveoakinteractive dot com and davidc at php dot net.  Static methods and variables, by definition, are bound to class types not object instances.  You should not need to dynamically find out what class a static method belongs to, since the context of your code should make it quite obvious.  Your questions reveals that you probably don't quite understand OOP quite yet (it took me a while as well).
Luke, the observed behavior from your particular code snippet makes perfect sense when you think about it.  The method getclass() is defined in BooBoof, so the __CLASS__ macro would be bound to BooBoof and defined in relation to the BooBoof class.  The fact that CooCoof is a subclass of BooBoof just means that it gains a shortcut to BooBoof::getclass().  So, in effect, you are really asking (in a convoluted way): "What is the class to which belongs the method call BooBoof::getclass()?"  The correct solution (if you actually want/need to do this) is to simply implement CooCoof::getclass() { return __CLASS__; } inside of the CooCoof definition, and any childclasses that you want to mimic this behavior.  CooCoof::getclass() will have the expected behavior.


wired

There is one unexpected bahaviour (for me as least):
<?php
 class parent
 {
   ...
   public function getInstance ($id)
   {
     ...
     print get_class() . "\n" . __CLASS__;
     ...
   }
 }
 class child extends parent
 {
   ...
 }
 child::getInstance(...);
?>
This code will produce:
 parent
 parent
So I can't make "new $className(...)" in getInstance(). The only option is to do a fabric.


marc w.

The previous comment (from matsgefvert dot se) is 100% correct. To further elaborate on the persistence layers example suggested, consider the case where you are dynamically creating inherited objects. For example:
<?php
class PersistedObject {
//...
public static function read($key){
//You will need the table name here to actually read
// from the persistence medium
echo get_class();
}
class SomeTable extends PersistedObject {
//...
}
/*
Somewhere else in our code we would like to call the read method
*/
$someTableObject = SomeTable::read(1234);
?>
Remember that the SomeTable class would be generated on the fly, probably by some DB schema. The problem is that you would actually like the above example to output "SomeTable", but unfortunately, it will output "PersistedObject".


refrozen dot com

philip at cornado dot com, it returns the value of the class from which it was called, rather than the instance's name... causing inheritance to result in unexpected returns

magicaltux

Note that the constant __CLASS__ is different from get_class($this) :
<?
 class test {
   function whoami() {
     echo "Hello, I'm whoami 1 !\r\n";
     echo "Value of __CLASS__ : ".__CLASS__."\r\n";
     echo "Value of get_class() : ".get_class($this)."\r\n\r\n";
   }
 }
 class test2 extends test {
   function whoami2() {
     echo "Hello, I'm whoami 2 !\r\n";
     echo "Value of __CLASS__ : ".__CLASS__."\r\n";
     echo "Value of get_class() : ".get_class($this)."\r\n\r\n";
     parent::whoami(); // call parent whoami() function
   }
 }
 $test=new test;
 $test->whoami();
 $test2=new test2;
 $test2->whoami();
 $test2->whoami2();
?>
The output is :
Hello, I'm whoami 1 !
Value of __CLASS__ : test
Value of get_class() : test
Hello, I'm whoami 1 !
Value of __CLASS__ : test
Value of get_class() : test2
Hello, I'm whoami 2 !
Value of __CLASS__ : test2
Value of get_class() : test2
Hello, I'm whoami 1 !
Value of __CLASS__ : test
Value of get_class() : test2
In fact, __CLASS__ returns the name of the class the function is in and get_class($this) returns the name of the class which was created.


benjaminhill

More funkyness:
class Parent {
  function displayTableName() {
     echo get_class($this);
     echo get_class();
  }
}
class Child {
  function __construct() {
     $this->displayTableName();
  }
}
Will return
- Child
- Parent
So when they say "the object isn't required in PHP5" - they don't really mean it.


bryan

janci's Singleton example is all well and good, until you create another class "Bar" which also extends Singleton.
<?php
$single_foo = Foo::getInstance();
$single_bar = Bar::getInstance();
?>
$single_bar will now be an instance of Foo! This is because there is only one copy of the static variable $__instance in the Singleton class. Here is a better Singleton class:
<?php
abstract class Singleton {
static $_instances = array();
//Prevent singletons from being instantiated other than via getInstance();
protected function __construct() {}
protected function __clone() {}
 
static function getInstance($class_name) {
if(!isset(self::$_instances[$class_name])) {
self::$_instances[$class_name] = new $class_name();
}
return self::$_instances[$class_name];
}
}?>
Unfortunately, you are still required to define Foo as janci does. I would love to see an example where the only thing you add to the class is "extends Singleton" and you're done, but that seems to be impossible.


kerry kobashi

It should be noted that class names are represented in lowercase under PHP 4.x.
class MyClass {
  function MyClass() {
  }
  function ShowClass() {
     echo get_class($this);
  }
}
$p = new MyClass();
$p->ShowClass();
Displays:
myclass
If you serialize $p, you will also see that the class name is lower case as well:
$p = new MyClass();
echo serialize($p);
Displays:
O:7:"myclass":1:{s:3:"val";i:100;}
In my case, this is an important point for mapping class names to database table names (and vice versa).


kunxin

I just migrated from PHP 4 to PHP 5 and noticed that in PHP 5.03 that a lot of code dependent on get_class() and its variants stop working.
It turns out that get_class() and its variants are now case-sensitive.


spam

I disagree with the notion that the authors of the previous posts are unfamiliar with OOP. Without the ability to know from general (parent) objects what kind of classes we're operating on, it makes things rather difficult, especially in building frameworks that rely heavily on class types (e.g. persistence layers).
The proposed BooBoof::getclass() and CooCoof::getclass() scheme will not work in some particular scenarios since static calls aren't virtual, which means a parent class will always call its own getclass() function instead of the one needed to find out the class name.
The only solution I've found is to pass along a string containing the class name we're working on to the generalized functions. It is however an ugly solution, certainly less than ideal and goes against what OOP and reflection is all about, IMHO.


colin

get_class() seems to actually return information about a prototype version of the class when called using $this as opposed to the working instance of the class. You must use "$this->$name" to get the info from this instance.
For example:
class myClass {
var myVar = "foo";
function myClass () {
$this->myVar = "bar";
}
function testClass () {
$vars = get_class_vars(get_class($this));
echo "Var myVar = ".$vars["myVar"].'<br/>';
}
function testClassAgain () {
$vars = get_class_vars(get_class($this));
echo "Var myVar = ".$this->myVar;
}
}
$instance = new myClass();
$instance->testClass();
$instance->testClassAgain();
Outputs:
foo
bar
This makes sense, but surprised me the first time I saw it.


frederik krautwald

Due to PHP 5 engine that permits to get final class in a static called function, and this is a modified version of examples published below.
<?php
abstract class Singleton {
   protected static $_instances = array();
 
   protected function __construct() {}
 
   protected static function getInstance() {
       $bt = debug_backtrace();
       $class = $bt[count($bt) - 1]['class'];
       if (!isset(self::$_instances[$class])) {
        self::$_instances[$class] = new $class();
       }
       return self::$_instances[$class];
   }
}
class A extends Singleton {
public static function getInstance() {
return parent::getInstance();
}
}
class B extends Singleton {
public static function getInstance() {
return parent::getInstance();
}
}
class C extends A {
public static function getInstance() {
return parent::getInstance();
}
}
$a = A::getInstance();
$b = B::getInstance();
$c = C::getInstance();
echo "\$a is a " . get_class($a) . "<br />";
echo "\$b is a " . get_class($b) . "<br />";
echo "\$c is a " . get_class($c) . "<br />";
?>
I don't know about if performance would increase if debug_backtrace() is skipped and instead have getInstance() to accept a passed class retrieved by get_class() method as parameter as described in a post below.
By having set getInstance() to protected in the Singleton class, the function is required to be overridden (good OOP practice).
One thing to mention is, that there is no error checking in case $class is null or undefined, which would result in a fatal error. At the moment, though, I can't see how it could happen when the getInstance() is protected, i.e. has to be overridden in a subclass -- but with good coding practice you should always error check.


makc dot the dot great

Check it out:
<?php
class A {
function s () { return "A::s"; }
function s1 () { return $this->s(); }
}
class B extends A {
function s () { return "B::s"; }
}
$a = new A(); echo $a->s1();
echo "
";
$b = new B(); echo $b->s1();
echo "
";
class C {
static function s () { return "C::s"; }
static function s1 () { return self::s(); }
}
class D extends C {
static function s () { return "D::s"; }
}
echo C::s1();
echo "
";
echo D::s1();
echo "
";
?>
Output:
A::s
B::s
C::s
C::s
Seems like static function always belong to its class.


davidc

As of php5, you cannot use get_class($this); in a public static function. You would have to do something like this:
<?php
class BooBoof {
   public static function getclass()
   {
       return __CLASS__;
   }
}
$c = BooBoof::getclass();
print $c;
?>
To get the class since you cannot use
<?php
public static function getclass()
{
   return get_class($this);
}
?>
Rather simple and straightforward but that might help some people that are searching for it..


philip

As of PHP 4.3.0 the constant __CLASS__ exists and contains the class name.

dodgie74

As noted in bug #30934 (which is not actually a bug but a consequence of a design decision), the "self" keyword is bound at compile time. Amongst other things, this means that in base class methods, any use of the "self" keyword will refer to that base class regardless of the actual (derived) class on which the method was invoked. This becomes problematic when attempting to call an overridden static method from within an inherited method in a derived class. For example:
<?php
class Base
{
protected $m_instanceName = '';

public static function classDisplayName()
{
return 'Base Class';
}

public function instanceDisplayName()
{
//here, we want "self" to refer to the actual class, which might be a derived class that inherits this method, not necessarily this base class
return $this->m_instanceName . ' - ' . self::classDisplayName();
}
}
class Derived extends Base
{
public function Derived( $name )
{
$this->m_instanceName = $name;
}

public static function classDisplayName()
{
return 'Derived Class';
}
}
$o = new Derived('My Instance');
echo $o->instanceDisplayName();
?>
In the above example, assuming runtime binding (where the keyword "self" refers to the actual class on which the method was invoked rather than the class in which the method is defined) would produce the output:
My Instance - Derived Class
However, assuming compile-time binding (where the keyword "self" refers to the class in which the method is defined), which is how php works, the output would be:
My Instance - Base Class
The oddity here is that "$this" is bound at runtime to the actual class of the object (obviously) but "self" is bound at compile-time, which seems counter-intuitive to me. "self" is ALWAYS a synonym for the name of the class in which it is written, which the programmer knows so s/he can just use the class name; what the programmer cannot know is the name of the actual class on which the method was invoked (because the method could be invoked on a derived class), which it seems to me is something for which "self" ought to be useful.
However, questions about design decisions aside, the problem still exists of how to achieve behaviour similar to "self" being bound at runtime, so that both static and non-static methods invoked on or from within a derived class act on that derived class. The get_class() function can be used to emulate the functionality of runtime binding for the "self" keyword for static methods:
<?php
class Base
{
protected $m_instanceName = '';

public static function classDisplayName()
{
return 'Base Class';
}

public function instanceDisplayName()
{
$realClass = get_class($this);
return $this->m_instanceName . ' - ' . call_user_func(array($realClass, 'classDisplayName'));
}
}
class Derived extends Base
{
public function Derived( $name )
{
$this->m_instanceName = $name;
}

public static function classDisplayName()
{
return 'Derived Class';
}
}
$o = new Derived('My Instance');
echo $o->instanceDisplayName();
?>
Output:
My Instance - Derived Class
I realise that some people might respond "why don't use just just the class name with ' Class' appended instead of the classDisplayName() method", which is to miss the point. The point is not the actual strings returned but the concept of wanting to use the real class for an overridden static method from within an inherited non-static method. The above is just a simplified version of a real-world problem that was too complex to use as an example.
Apologies if this has been mentioned before.


bramus

@ Frederik :
<?
$class = $bt[count($bt) - 1]['class'];
?>
should be
<?
$class = $bt[count($bt) - 2]['class'];
?>
;-)


Change Language


Follow Navioo On Twitter
call_user_method_array
call_user_method
class_exists
get_class_methods
get_class_vars
get_class
get_declared_classes
get_declared_interfaces
get_object_vars
get_parent_class
interface_exists
is_a
is_subclass_of
method_exists
property_exists
eXTReMe Tracker