I am trying to access a static method, but using a variable as the class name. Is this possible? I seem to be having issues with it. I want to be able to do something like this:
class foo {
public static function bar() {
echo 'test';
}
}
$variable_class_name = 'foo';
$variable_class_name::bar();
And I want to be able to do similar using static variables as well.
That syntax is only supported in PHP 5.3 and later. Previous versions don't understand that syntax, hence your parse error (T_PAAMAYIM_NEKUDOTAYIM refers to the :: operator).
In previous versions you can try call_user_func(), passing it an array containing the class name and its method name:
$variable_class_name = 'foo';
call_user_func(array($variable_class_name, 'bar'));
You can use reflection for PHP 5.1 and above:
class foo {
public static $bar = 'foobar';
}
$class = 'foo';
$reflector = new ReflectionClass($class);
echo $reflector->getStaticPropertyValue('bar');
> foobar
Related
I'm trying to access a class constant in one of my classes:
const MY_CONST = "value";
If I have a variable which holds the name of this constant like this:
$myVar = "MY_CONST";
Can I access the value of MY_CONST somehow?
self::$myVar
does not work obviously because it is for static properties.
Variable variables does not work either.
There are two ways to do this: using the constant function or using reflection.
Constant Function
The constant function works with constants declared through define as well as class constants:
class A
{
const MY_CONST = 'myval';
static function test()
{
$c = 'MY_CONST';
return constant('self::'. $c);
}
}
echo A::test(); // output: myval
Reflection Class
A second, more laborious way, would be through reflection:
$ref = new ReflectionClass('A');
$constName = 'MY_CONST';
echo $ref->getConstant($constName); // output: myval
There is no syntax for that, but you can use an explicit lookup:
print constant("classname::$myConst");
I believe it also works with self::.
Can I access the value of MY_CONST somehow?
self::MY_CONST
If you want to access is dynamically, you can use the reflection API Docs:
$myvar = 'MY_CONST';
$class = new ReflectionClass(self);
$const = $class->getConstant($myVar);
The benefit with the reflection API can be that you can get all constants at once (getConstants).
If you dislike the reflection API because you don't wanna use it, an alternative is the constant function (Demo):
$myvar = 'MY_CONST';
class foo {const MY_CONST = 'bar';}
define('self', 'foo');
echo constant(self.'::'.$myvar);
Just a note for Reflection: the constructor for ReflectionClass must receive the full path of the class for its parameter.
This means that just setting the string 'A' as a constructor parameter may not work in some cases.
To avoid this problem, when using ReflectionClass you will be better if you do this:
$classA = new A();
$name_classA = get_class($classA);
$ref = new ReflectionClass(get_class($name_classA));
$constName = 'MY_CONST';
echo $ref->getConstant($constName);
Function get_class will give you the full path of a class whenever you are in the code. Missing the full path may result in a "Class not found" PHP error.
have you tried
$myVar = MY_CONST or $myVar = $MY_CONST
I'm trying to access a class constant in one of my classes:
const MY_CONST = "value";
If I have a variable which holds the name of this constant like this:
$myVar = "MY_CONST";
Can I access the value of MY_CONST somehow?
self::$myVar
does not work obviously because it is for static properties.
Variable variables does not work either.
There are two ways to do this: using the constant function or using reflection.
Constant Function
The constant function works with constants declared through define as well as class constants:
class A
{
const MY_CONST = 'myval';
static function test()
{
$c = 'MY_CONST';
return constant('self::'. $c);
}
}
echo A::test(); // output: myval
Reflection Class
A second, more laborious way, would be through reflection:
$ref = new ReflectionClass('A');
$constName = 'MY_CONST';
echo $ref->getConstant($constName); // output: myval
There is no syntax for that, but you can use an explicit lookup:
print constant("classname::$myConst");
I believe it also works with self::.
Can I access the value of MY_CONST somehow?
self::MY_CONST
If you want to access is dynamically, you can use the reflection API Docs:
$myvar = 'MY_CONST';
$class = new ReflectionClass(self);
$const = $class->getConstant($myVar);
The benefit with the reflection API can be that you can get all constants at once (getConstants).
If you dislike the reflection API because you don't wanna use it, an alternative is the constant function (Demo):
$myvar = 'MY_CONST';
class foo {const MY_CONST = 'bar';}
define('self', 'foo');
echo constant(self.'::'.$myvar);
Just a note for Reflection: the constructor for ReflectionClass must receive the full path of the class for its parameter.
This means that just setting the string 'A' as a constructor parameter may not work in some cases.
To avoid this problem, when using ReflectionClass you will be better if you do this:
$classA = new A();
$name_classA = get_class($classA);
$ref = new ReflectionClass(get_class($name_classA));
$constName = 'MY_CONST';
echo $ref->getConstant($constName);
Function get_class will give you the full path of a class whenever you are in the code. Missing the full path may result in a "Class not found" PHP error.
have you tried
$myVar = MY_CONST or $myVar = $MY_CONST
I have a question regarding "dynamic" class initialising, let me explain what I mean:
$class = 'User';
$user = new $class();
//...is the same as doing
$user = new User();
So... that's not the problem, but I am having some trouble doing the same while calling a static variable from a class, for example:
$class = 'User';
print $class::$name;
Which gives out the following error:
Parse error: syntax error, unexpected T_PAAMAYIM_NEKUDOTAYIM in
Off course I have tested doing print User::$name; and that works. So class works.
Why is this and is there a way around it?
Follow up question:
Also is there any valid reasons to not use this "dynamic" way in creating classes?
This code works good on PHP 5.4.3:
<?php
class A {
public static $var = "Hello";
}
print(A::$var);
$className = "A";
print($className::$var);
?>
This is the answer from the question I linked in the comments:
You can use reflection to do this. Create a ReflectionClass
object given the classname, and then use the getStaticPropertyValue
method to get the static variable value.
class Demo
{
public static $foo = 42;
}
$class = new ReflectionClass('Demo');
$value=$class->getStaticPropertyValue('foo');
var_dump($value);
If you don't have PHP version of 5.3 and above, and you don't want to use reflection (which in my opinion is an overkill - unless you want to access multiple static properties) you can define getter function and call it via call_user_func():
class A {
public static $var = "Hello";
public static function getVar() {
return self::$var;
}
}
$className = "A";
echo call_user_func(array($className, 'getVar'));
I'm trying to access a class constant in one of my classes:
const MY_CONST = "value";
If I have a variable which holds the name of this constant like this:
$myVar = "MY_CONST";
Can I access the value of MY_CONST somehow?
self::$myVar
does not work obviously because it is for static properties.
Variable variables does not work either.
There are two ways to do this: using the constant function or using reflection.
Constant Function
The constant function works with constants declared through define as well as class constants:
class A
{
const MY_CONST = 'myval';
static function test()
{
$c = 'MY_CONST';
return constant('self::'. $c);
}
}
echo A::test(); // output: myval
Reflection Class
A second, more laborious way, would be through reflection:
$ref = new ReflectionClass('A');
$constName = 'MY_CONST';
echo $ref->getConstant($constName); // output: myval
There is no syntax for that, but you can use an explicit lookup:
print constant("classname::$myConst");
I believe it also works with self::.
Can I access the value of MY_CONST somehow?
self::MY_CONST
If you want to access is dynamically, you can use the reflection API Docs:
$myvar = 'MY_CONST';
$class = new ReflectionClass(self);
$const = $class->getConstant($myVar);
The benefit with the reflection API can be that you can get all constants at once (getConstants).
If you dislike the reflection API because you don't wanna use it, an alternative is the constant function (Demo):
$myvar = 'MY_CONST';
class foo {const MY_CONST = 'bar';}
define('self', 'foo');
echo constant(self.'::'.$myvar);
Just a note for Reflection: the constructor for ReflectionClass must receive the full path of the class for its parameter.
This means that just setting the string 'A' as a constructor parameter may not work in some cases.
To avoid this problem, when using ReflectionClass you will be better if you do this:
$classA = new A();
$name_classA = get_class($classA);
$ref = new ReflectionClass(get_class($name_classA));
$constName = 'MY_CONST';
echo $ref->getConstant($constName);
Function get_class will give you the full path of a class whenever you are in the code. Missing the full path may result in a "Class not found" PHP error.
have you tried
$myVar = MY_CONST or $myVar = $MY_CONST
I know this question sounds rather vague so I will make it more clear with an example:
$var = 'bar';
$bar = new {$var}Class('var for __construct()'); //$bar = new barClass('var for __construct()');
This is what I want to do. How would you do it? I could off course use eval() like this:
$var = 'bar';
eval('$bar = new '.$var.'Class(\'var for __construct()\');');
But I'd rather stay away from eval(). Is there any way to do this without eval()?
Put the classname into a variable first:
$classname=$var.'Class';
$bar=new $classname("xyz");
This is often the sort of thing you'll see wrapped up in a Factory pattern.
See Namespaces and dynamic language features for further details.
If You Use Namespaces
In my own findings, I think it's good to mention that you (as far as I can tell) must declare the full namespace path of a class.
MyClass.php
namespace com\company\lib;
class MyClass {
}
index.php
namespace com\company\lib;
//Works fine
$i = new MyClass();
$cname = 'MyClass';
//Errors
//$i = new $cname;
//Works fine
$cname = "com\\company\\lib\\".$cname;
$i = new $cname;
How to pass dynamic constructor parameters too
If you want to pass dynamic constructor parameters to the class, you can use this code:
$reflectionClass = new ReflectionClass($className);
$module = $reflectionClass->newInstanceArgs($arrayOfConstructorParameters);
More information on dynamic classes and parameters
PHP >= 5.6
As of PHP 5.6 you can simplify this even more by using Argument Unpacking:
// The "..." is part of the language and indicates an argument array to unpack.
$module = new $className(...$arrayOfConstructorParameters);
Thanks to DisgruntledGoat for pointing that out.
class Test {
public function yo() {
return 'yoes';
}
}
$var = 'Test';
$obj = new $var();
echo $obj->yo(); //yoes
I would recommend the call_user_func() or call_user_func_arrayphp methods.
You can check them out here (call_user_func_array , call_user_func).
example
class Foo {
static public function test() {
print "Hello world!\n";
}
}
call_user_func('Foo::test');//FOO is the class, test is the method both separated by ::
//or
call_user_func(array('Foo', 'test'));//alternatively you can pass the class and method as an array
If you have arguments you are passing to the method , then use the call_user_func_array() function.
example.
class foo {
function bar($arg, $arg2) {
echo __METHOD__, " got $arg and $arg2\n";
}
}
// Call the $foo->bar() method with 2 arguments
call_user_func_array(array("foo", "bar"), array("three", "four"));
//or
//FOO is the class, bar is the method both separated by ::
call_user_func_array("foo::bar"), array("three", "four"));