Continuous methods php [duplicate] - php

This question already has answers here:
PHP method chaining or fluent interface?
(10 answers)
Closed 7 years ago.
I see in codeigniter a sintaxis method->other_method->other_method_again. example:
$this->db->select()->join()->findAll();
When i try
class MyClass{
public function bla(){
echo "bla";
}
public function other(){
echo "other";
}
}
$message = new MyClass();
$message->bla()->other();
Return:
Fatal error: Call to a member function other()
as I can do what codeigniter?

this is called method chaining (popularised by jQuery chaining) and is achieved if you
return $this
from each method
for your example:
class MyClass{
public function bla(){
echo "bla";
return $this; // enable method chaining
}
public function other(){
echo "other";
return $this; // enable method chaining
}
}
The reason this works is the same the following works:
$instance->method1();
$instance->method2();
Here each method is called on an $instance but if each method returns the actual $instance back which is the same as $this, then one can combine the statements like this ("chain" them):
$instance->method1()/* returns $instance and can be used again*/->method2();
That's all there is to it.

Related

How to echo an object? [duplicate]

This question already has answers here:
How to echo a custom object in PHP?
(4 answers)
Closed 3 years ago.
Please i need to create a functions and call them in one line using -> between them
I have this code but it doesn't run
<?php
class A {
public $a2;
public $b2;
public function mohamed($a){
$this->a2 = $a;
return $this ;
}
public function test($b){
$this->b2 = $b;
return $this ;
}
}
$class = new A();
echo $class->mohamed('name')->test('mohamed');;
?>
Since your class doesn't have a __toString() method, you cannot echo the class object itself.
So you have a few alternatives here, either declare a __toString() method that prints what you want it to, or print the variables separately.
Example using the magic-method __toString() (demo at https://3v4l.org/NPp2L) - you can now echo $class.
public function __tostring() {
return "A2 is '".$this->a2."' and B2 is '".$this->b2."'";
}
Alternative two is to not print the class itself, but get the properties of the class instead. Since they are public, you don't need a getter-method to use them in the public scope.
$class = new A();
$class->mohamed('name')->test('mohamed');;
echo $class->a2." and ".$class->b2;
Demo at https://3v4l.org/nHeP9
If I run your code the error explains the problem :
Object of class A could not be converted to string
Your function test() returns $this, a class A object which can not be echoed.
Try implement a __toString() function, or use a var_dump() instead of your echo to check your object's properties.
No matter what, your code and your chaining is working fine.
Actually, above code is running but you can not echo an object also you can try "var_dump()" instead of "echo".
var_dump($class->mohamed('name')->test('mohamed'));
Try this:
<?php
class A {
public $a2;
public $b2;
public function mohamed($a){
$this->a2 = $a;
return $this ;
}
public function test($b){
$this->b2 = $b;
return $this ;
}
}
$class = new A();
var_dump($class);
?>

Using constructor and a public function in a class [duplicate]

This question already has answers here:
When would you use the $this keyword in PHP?
(12 answers)
Closed 9 years ago.
I tried to create a basic class with a function. Once an instance of the class is created new BaseClass("hello") then the constructor function saves the parameter to a variable.
The ->ret_text() should return with this variable, but it doesn't works. The error is: unexpected T_OBJECT_OPERATOR
class BaseClass {
var $txt;
function __construct($text) {
$txt = $text;
}
public function ret_text() {
return $txt;
}
}
echo (new BaseClass("hello"))->ret_text();
You should access your class variables with $this->variableName where $this refers to the class you are in.
In your example $txt is not the class variable $txt but only a variable for the current function (__construct(), ret_text() or something else). Also you can't call a method directly after the initialization of the class, i.e. (new Class())->methodName(); will not work for PHP version < 5.4. However, it will work for PHP version => 5.4.
Instead try this:
class BaseClass {
var $txt;
function __construct($text) {
$txt = 'This is a variable only for this method and it\'s not $this->txt.';
$this->txt = $text;
}
public function ret_text() {
$txt = 'This is a variable only for this method and it\'s not $this->txt.';
return $this->txt;
}
}
$bc = new BaseClass("hello");
echo $bc->ret_text();

How do I chain methods in PHP? [duplicate]

This question already has answers here:
PHP method chaining or fluent interface?
(10 answers)
Closed 7 years ago.
jQuery lets me chain methods. I also remember seeing the same in PHP so I wrote this:
class cat {
function meow() {
echo "meow!";
}
function purr() {
echo "purr!";
}
}
$kitty = new cat;
$kitty->meow()->purr();
I cannot get the chain to work. It generates a fatal error right after the meow.
To answer your cat example, your cat's methods need to return $this, which is the current object instance. Then you can chain your methods:
class cat {
function meow() {
echo "meow!";
return $this;
}
function purr() {
echo "purr!";
return $this;
}
}
Now you can do:
$kitty = new cat;
$kitty->meow()->purr();
For a really helpful article on the topic, see here: http://www.talkphp.com/advanced-php-programming/1163-php5-method-chaining.html
Place the following at the end of each method you wish to make "chainable":
return $this;
Just return $this from your method, i.e. (a reference to) the object itself:
class Foo()
{
function f()
{
// ...
return $this;
}
}
Now you can chain at heart's content:
$x = new Foo;
$x->f()->f()->f();
yes using php 5 you can return object from a method. So by returning $this (which points to the current object), you can achieve method chaining

Static array variable of another class' objects does not allow calling methods of the second class [duplicate]

This question already has answers here:
Call to a member function on a non-object [duplicate]
(8 answers)
Closed 10 years ago.
I am can't figure out why this doesn't work:
class Test
{
public static $arData=array();
public static function addMember(Person $member)
{
self::$arData[]=$member;
}
public static function showAll()
{
for($i=0;$i<count(self::$arData);$i++)
{
self::$arData[i]->show();
}
}
}
What I get is this: Fatal error: Call to a member function show() on a non-object.
The show() method does exist and it basically prints out name and location of a person.
In in the constructor, instead of adding $member to $arData I do $member->show() it works.
So... what's up?
Try
self::$arData[$i]->show();
How about this:
foreach (self::$arData as $person) {
$person->show();
}
The error is in the for-loop:
...
public static function showAll()
{
for($i=0;$i<count(self::$arData);$i++)
{
self::$arData[$i]->show();
}
}
...
It must be $i and not only i in the array-access-operator when calling the show()-method.

Calling anonymous functions defined as object variables in php [duplicate]

This question already has answers here:
Calling closure assigned to object property directly
(12 answers)
Closed 9 years ago.
I have php code like:
class Foo {
public $anonFunction;
public function __construct() {
$this->anonFunction = function() {
echo "called";
}
}
}
$foo = new Foo();
//First method
$bar = $foo->anonFunction();
$bar();
//Second method
call_user_func($foo->anonFunction);
//Third method that doesn't work
$foo->anonFunction();
Is there a way in php that I can use the third method to call anonymous functions defined as class properties?
thanks
Not directly. $foo->anonFunction(); does not work because PHP will try to call the method on that object directly. It will not check if there is a property of the name storing a callable. You can intercept the method call though.
Add this to the class definition
public function __call($method, $args) {
if(isset($this->$method) && is_callable($this->$method)) {
return call_user_func_array(
$this->$method,
$args
);
}
}
This technique is also explained in
JavaScript-style object literals

Categories