php oop call method from inside the method from the same class - php

I've got the following issue
class class_name {
function b() {
// do something
}
function c() {
function a() {
// call function b();
}
}
}
When I call function as usual: $this->b(); I get this error: Using $this when not in object context in C:...
function b() is declared as public
any thoughts?
I'll appreciate any help
Thanks

The function a() is declared inside method c().
<?php
class class_name {
function b() {
echo 'test';
}
function c() {
}
function a() {
$this->b();
}
}
$c = new class_name;
$c->a(); // Outputs "test" from the "echo 'test';" call above.
Example using a function inside a method (not recommended)
The reason why your original code wasn't working is because of scope of variables. $this is only available within the instance of the class. The function a() is not longer part of it so the only way to solve the problem is to pass the instance as a variable to the class.
<?php
class class_name {
function b() {
echo 'test';
}
function c() {
// This function belongs inside method "c". It accepts a single parameter which is meant to be an instance of "class_name".
function a($that) {
$that->b();
}
// Call the "a" function and pass an instance of "$this" by reference.
a(&$this);
}
}
$c = new class_name;
$c->c(); // Outputs "test" from the "echo 'test';" call above.

Related

How to call a variable function in php within a class?

I have the following example code
<?php
class Test {
function foo() {
print "foo\n";
}
function bar() {
$func = 'foo';
$func();
}
}
$test = new Test();
$test->bar()
which calls $test-bar(), whiich internally calls a variable php function named foo. This variable contains the string foo and I want the function foo be called like here. Instead of getting the expected output
foo
I get an error:
PHP Fatal error: Call to undefined function foo() ...
How to do this right, when using a string for the function-name? The string 'func' might denote several different functions inside the class scope in the actual code.
According to the doc the above should work like I have coded, more or less...
<?php
class Test {
public function foo() {
print "foo\n";
}
public function bar() {
$func = 'foo';
$this->$func();
}
}
$test = new Test();
$test->bar();
?>
Use this for accessing the current function of this class
What you can do is use the function call_user_func() to invoke the callback.
<?php
class Test {
public function foo() {
print "foo\n";
}
public function bar() {
$func = 'foo';
call_user_func(array($this, $func));
}
}
$test = new Test();
$test->bar();
You use the keyword $this
<?php
class Test {
function foo() {
print "foo\n";
}
function bar() {
$this->foo(); // you can do this
}
}
$test = new Test();
$test->bar()
There are two ways to call a method from a string input:
$methodName = "foo";
$this->$methodName();
Or you can use call_user_func_array()
call_user_func_array("foo",$args); // args is an array of your arguments
or
call_user_func_array(array($this,"foo"),$args); // will call the method in this scope

Use Class property inside of a method's function

I'm trying to use myVar inside my of a method's function. I have already tried adding global but still nothing. I know this is probably basic but I can't seem to find it.
class myClass{
public $myVar;
public function myFunction() {
function myInnerFunction() {
//how do I use this variable here
echo $this->myVar;
}
}
}
Whenever I try using $this I get this error: 'Using $this when not in object context in...'
You should use $this->myVar
See the PHP Documentation - The Basics
<?php
class SimpleClass
{
// property declaration
public $var = 'a default value';
// method declaration
public function displayVar() {
echo $this->var;
}
}
?>
The pseudo-variable $this is available when a method is called from
within an object context. $this is a reference to the calling object
(usually the object to which the method belongs
Update:
In your new code sample, myInnerFunction is a nested function and is not accessible until the myFunction method is called. Once the myFunction method is called, the myInnerFunction becomes part of the global scope.
Maybe this is what you are looking for:
class myClass{
public $myVar;
public function myFunction() {
}
function myInnerFunction() {
//how do I use this variable here
echo $this->myVar;
}
}
Inner functions like myInnerFunction are always global in scope, even if they are defined inside of a member function in a class. See this question for another similar example
So, to PHP, the following are (almost) equivalent:
class myClass{
public $myVar;
public function myFunction() {
function myInnerFunction() {
//how do I use this variable here
echo $this->myVar;
}
}
}
And
class myClass{
public $myVar;
public function myFunction() {
}
}
function myInnerFunction() {
//how do I use this variable here
echo $this->myVar;
}
Hopefully the second example illustrates why $this is not even in scope for myInnerFunction. The solution is simply to pass the variable as a parameter to the function.
Pass it as an argument to the inner function.
You can use ReflectionProperty:
$prop = new ReflectionProperty("SimpleClass", 'var');
Full example:
class myClass{
public $myVar;
public function myFunction() {
function myInnerFunction() {
//how do I use this variable here
$prop = new ReflectionProperty("SimpleClass", 'myVar');
}
}
}
The solution above is good when you need each instance to have an own value. If you need all instances to have a same you can use static:
class myClass
{
public static $myVar = "this is my var's value";
public function myClass() {
echo self::$myVar;
}
}
new myClass();
see here

How to call the __invoke method of a member variable inside a class

PHP 5.4.5, here. I'm trying to invoke an object which is stored as a member of some other object. Like this (very roughly)
class A {
function __invoke () { ... }
}
class B {
private a = new A();
...
$this->a(); <-- runtime error here
}
This produces a runtime error, of course, because there's no method called a. But if I write the call like this:
($this->a)();
then I get a syntax error.
Of course, I can write
$this->a->__invoke();
but that seems intolerably ugly, and rather undermines the point of functors. I was just wondering if there is a better (or official) way.
There's three ways:
Directly calling __invoke, which you already mentioned:
$this->a->__invoke();
By assigning to a variable:
$a = $this->a;
$a();
By using call_user_func:
call_user_func($this->a);
The last one is probably what you are looking for. It has the benefit that it works with any callable.
FYI in PHP 7+ parenthesis around a callback inside an object works now:
class foo {
public function __construct() {
$this -> bar = function() {
echo "bar!" . PHP_EOL;
};
}
public function __invoke() {
echo "invoke!" . PHP_EOL;
}
}
(new foo)();
$f = new foo;
($f -> bar)();
Result:
invoke!
bar!
I know this is a late answer, but use a combination of __call() in the parent and __invoke() in the subclass:
class A {
function __invoke ($msg) {
print $msg;
}
}
class B {
private $a;
public function __construct() { $this->a = new A(); }
function __call($name, $args)
{
if (property_exists($this, $name))
{
$prop = $this->$name;
if (is_callable($prop))
{
return call_user_func_array($prop, $args);
}
}
}
}
Then you should be able to achieve the syntactic sugar you are looking for:
$b = new B();
$b->a("Hello World\n");

PHP Classes calling functions to it

I saw some codes that when they call php functions from another class they no longer use $this->functionName(),
they just refer immedietly to the function name, like functionName()
In my index.php
$help = new Helper();
$help->Test();
I wanted to call Test Function by not doing the $help.
How can this be done? Why is this possible?
In PHP you can mix a procedural style of programming with object oriented style. That means that function can either exist as member of a class, or as stand-alone functions.
Member functions (or methods) are are called using $classinstance->methodname() for normal (instance) methods, or ClassName::methodName() for static methods.
Standalone functions are just called without referring to a class or object whatsoever. You can put them in separate files, if you like.
The declaration and usage is as follows:
In example.php:
class MyClass
{
$member = 'Hello world';
function MyMethod()
{
// The method can use the instance variable (member variable)
// using $this to refer to the instance of the class
echo $this->member;
}
static function MyStaticMethod()
{
echo 'Hello static world';
}
}
function MyFunction()
{
echo 'Hello';
}
In index.php:
// To include the class and its methods, as well as the function.
require_once 'example.php';
// Call an instance method
$instance = new MyClass();
$instance->MyMethod();
// Call a static method
MyClass::MyStaticMethod();
// Call a stand-alone function
MyFunction();
A standalone function is defined like this:
function myfunction() {
# whatever
}
Also see http://www.php.net/manual/en/functions.user-defined.php
With the -> operator you reference a function from within a class.
<?php
class A {
public function a() {
$this->b(); //references the function b() in $this class
}
public function b() {
echo 'Was called from function a() in class A';
}
}
function c() {
echo "I'm just a simple function outside a class";
}
//now you can do following calls
$class_a = new A();
$class_a->a();
c(); //references function c() within the same scope
The output would be:
Was called from function a() in class A
I'm just a simple function outside a class
But you could also do the following: outsource the function c() into an external file like function_c.php
Now, you can include/require the file from anywhere else and use it's content:
include 'function_c.php';
c(); //the function is now available, although it was defined in another file
you can a function from another class from a class, example:
require "myExternClass.php";
class myClass extends myExternClass
{
public function a() {
$this->b(); /* function b is in the class myExternClass */
}
}
generally you can't call a method of an object without the object itself.
but for some cases when method does not actually uses any objects' properties it may be acceptable for testing purposes to invoke it with call_user_func_array, passing some dummy value instead of object.
class A {
var $a;
function doNop() { echo "Nop";}
function doA() { echo "[".$a."]"; }
}
// instead of this
$a = new A;
$a->doNop();
// you _may_ use this
A::doNop();
// but this will fail, because there's no object to apply doA() to.
A::doA();
class A_dummy { $a };
// however, for testing purposes you can provide a dummy instead of real A instance
$b = new A_dummy;
call_user_func(array($b, 'A::doA'));
You can wrap the code in question inside a regular function:
function TestClass() {
$help = new Helper();
return $help->Test();
}
Then, in your index.php file you can call the function like this:
TestClass();

Call to undefined function handler

Is it possible to handle this type of errors? Something like spl_autoload_register, but for functions.
Basically, what I am trying to do:
I have the class:
class Foo {
public function bar() {
echo 1;
}
}
So, when I call a nonexistent function Foo() like this:
Foo()->bar();
The possible handler should create a function Foo(), which looks like that:
function Foo() {
return new Foo();
}
If you never need an actual instance of the object, why not use a static class?
class Foo {
public static function bar() {
echo 1;
}
}
Foo::bar();
Then, you can do this in your app:
$this->fiends = FriendsModel::getUserFriends($userId);

Categories