Change the value of $this in PHP - php

I'm developing a program that has to do with Question asking, so imagine there's the Question class. If I wanted to refer to a static function in Question which creates a Question item could I assign this object to $this variable?
In a more general perspective
Is it possible to change the value of $this variable of a class? If yes, how can you do that? Otherwise why can't I hook $this to another object of same class?

The pseudo-variable $this is a reference to the calling object. Trying to re-assign it will generate a fatal error.
PHP manual: http://php.net/manual/en/language.oop5.basic.php
Similar question: PHP Fatal error: Cannot re-assign $this

So, I think you are a little foggy on what $this is for. It is simply a way to refer to the instance of the class that is being utilized. This reference only occurs within the class.
For example:
class Question
{
function __construct($question, $correctAnswer)
{
$this->question = $question;
$this->correctAnswer = $correctAnswer;
}
function answerQuestion($answer)
{
if ($answer == $this->correctAnswer) {
return true;
} else {
return false;
}
}
}
Notice to determine if the answer is correct we compare the provided answer against:
$this->correctAnswer
If we create two different questions:
$questionOne = new Question("Who is the founder of Microsoft?", "Bill Gates");
$questionTwo = new Question("Who is the CEO of Apple, Inc?", "Tim Cook");
And provide the same answer, we get different results:
$isCorrect = $questionOne->answerQuestion("Tim Cook"); // FALSE
$isCorrect = $questionTwo->answerQuestion("Tim Cook"); // TRUE
This is because $this refers to the instance being used.
So, within the class, you use $this.
Outside the class, you use the object name. In this case: $questionOne or $questionTwo
I hope that helps clear things up.

Related

Get time difference between db time values and today's time in mysql [duplicate]

This question already has answers here:
Reference - What does this error mean in PHP?
(38 answers)
Closed 8 years ago.
So I'm refactoring my code to implement more OOP. I set up a class to hold page attributes.
class PageAtrributes
{
private $db_connection;
private $page_title;
public function __construct($db_connection)
{
$this->db_connection = $db_connection;
$this->page_title = '';
}
public function get_page_title()
{
return $this->page_title;
}
public function set_page_title($page_title)
{
$this->page_title = $page_title;
}
}
Later on I call the set_page_title() function like so
function page_properties($objPortal) {
$objPage->set_page_title($myrow['title']);
}
When I do I receive the error message:
Call to a member function set_page_title() on a non-object
So what am I missing?
It means that $objPage is not an instance of an object. Can we see the code you used to initialize the variable?
As you expect a specific object type, you can also make use of PHPs type-hinting featureDocs to get the error when your logic is violated:
function page_properties(PageAtrributes $objPortal) {
...
$objPage->set_page_title($myrow['title']);
}
This function will only accept PageAtrributes for the first parameter.
There's an easy way to produce this error:
$joe = null;
$joe->anything();
Will render the error:
Fatal error: Call to a member function anything() on a non-object in /Applications/XAMPP/xamppfiles/htdocs/casMail/dao/server.php on line 23
It would be a lot better if PHP would just say,
Fatal error: Call from Joe is not defined because (a) joe is null or (b) joe does not define anything() in on line <##>.
Usually you have build your class so that $joe is not defined in the constructor or
Either $objPage is not an instance variable OR your are overwriting $objPage with something that is not an instance of class PageAttributes.
It could also mean that when you initialized your object, you may have re-used the object name in another part of your code. Therefore changing it's aspect from an object to a standard variable.
IE
$game = new game;
$game->doGameStuff($gameReturn);
foreach($gameArray as $game)
{
$game['STUFF']; // No longer an object and is now a standard variable pointer for $game.
}
$game->doGameStuff($gameReturn); // Wont work because $game is declared as a standard variable. You need to be careful when using common variable names and were they are declared in your code.
function page_properties($objPortal) {
$objPage->set_page_title($myrow['title']);
}
looks like different names of variables $objPortal vs $objPage
I recommend the accepted answer above. If you are in a pinch, however, you could declare the object as a global within the page_properties function.
$objPage = new PageAtrributes;
function page_properties() {
global $objPage;
$objPage->set_page_title($myrow['title']);
}
I realized that I wasn't passing $objPage into page_properties(). It works fine now.
you can use 'use' in function like bellow example
function page_properties($objPortal) use($objPage){
$objPage->set_page_title($myrow['title']);
}

$this acting alone in the php code

I have been confused by $this.I know $this->somevaribale used for refering global values...But i have seen a code like
class ClassName
{
private $array; //set up a variable to store our array
/*
* You can set your own array or use the default one
* it will set the $this->array variable to whatever array is given in the construct
* How the array works like a database; array('column_name' => 'column_data')
*/
function __construct($array = array('fruit' => 'apple', 'vegetable' => 'cucumber')) {
$this->array = $array;
}
/*
* Loops through the array and sets new variables within the class
* it returns $this so that you may chain the method.
*/
public function execute() {
foreach($this->array AS $key => $value) {
$this->$key = $value; //we create a variable within the class
}
return $this; //we return $this so that we can chain our method....
}
}
Here $this is called alone ...Am really confused with this..When i remove $this and replaced with $this->array i get error..
So my question is what is the use of calling $this alone and what it represents.
Thanx for the help.
$This is a reference for PHP Objects. You can learn more about objects and how $this works in the PHP manual here.
A class is a kind of "blueprint" of an object, and vice versa, and object is an instance of a class. When $this is used within the class, it refers to itself.
$hi = new ClassName();
$hi->execute()->method()->chaining()->is_like_this();
$hi refers to a ClassName object, and the function execute() returns the object itself.
$ha = $hi->execute();
// $ha refers to a ClassName object.
Method chaining (fluent interfaces) enables one to tidy up the code if one normally calls many methods of that object:
$hi->doSome();
$hi->doAnotherThing();
$hi->thirdMethodCall();
$hi->etcetera();
will become
$hi->doSome()
->doAnotherThing()
->thirdMethodCall()
->etcetera();
A couple of corrections to the terms you use:
$this is a reference to the "current" object, not "global values"
you're not "calling" anything here; functions are called, you're just using $this (which, again, is a variable holding an object)
So, return $this returns the current object as return value of the method. This is usually just done to facilitate fluent interfaces, a style where you can write code like:
$foo->bar()->baz()
Because bar() returns an object (the $this object), you can call its method baz() right afterwards.

Is is possible to store a reference to an object method?

Assume this class code:
class Foo {
function method() {
echo 'works';
}
}
Is there any way to store a reference to the method method of a Foo instance?
I'm just experimenting and fiddling around, my goal is checking whether PHP allows to call $FooInstance->method() without writing $FooInstance-> every time. I know I could write a function wrapper for this, but I'm more interested in getting a reference to the instance method.
For example, this pseudo-code would theoretically store $foo->method in the $method variable:
$foo = new Foo();
$method = $foo->method; //Undefined property: Foo::$method
$method();
Apparently, as method is a method and I'm not calling it with () the interpreter thinks I'm looking for a property thus this doesn't work.
I've read through Returning References but the examples only show how to return references to variables, not methods.
Therefore, I've adapted my code to store an anonymous function in a variable and return it:
class Foo {
function &method() {
$fn = function() {
echo 'works';
};
return $fn;
}
}
$foo = new Foo();
$method = &$foo->method();
$method();
This works, but is rather ugly. Also, there's no neat way to call it a single time, as this seems to require storing the returned function in a variable prior to calling it: $foo->method()(); and ($foo->method())(); are syntax errors.
Also, I've tried returning the anonymous function directly without storing it in a variable, but then I get the following notice:
Notice: Only variable references should be returned by reference
Does this mean that returning/storing a reference to a class instance method is impossible/discouraged or am I overlooking something?
Update: I don't mind adding a getter if necessary, the goal is just getting a reference to the method. I've even tried:
class Foo {
var $fn = function() {
echo 'works';
};
function &method() {
return $this->fn;
}
}
But from the unexpected 'function' (T_FUNCTION) error I'd believe that PHP wisely doesn't allow properties to store functions.
I'm starting to believe that my goal isn't easily achievable without the use of ugly hacks as eval().
It is. You have to use an array, with two values: the class instance (or string of the class name if you are calling a static method) and the method name as a string. This is documented on the Callbacks Man page:
A method of an instantiated object is passed as an array containing an object at index 0 and the method name at index 1.
Demo (Codepad):
<?php
class Something {
public function abc() {
echo 'called';
}
}
$some = new Something;
$meth = array($some, 'abc');
$meth(); // 'called'
Note this is also works with the built-ins that require callbacks (Codepad):
class Filter {
public function doFilter($value) {
return $value !== 3;
}
}
$filter = new Filter;
$test = array(1,2,3,4,5);
var_dump(array_filter($test, array($filter, 'doFilter'))); // 'array(1,2,4,5)'
And for static methods -- note the 'Filter' instead of an instance of a class as the first element in the array (Codepad):
class Filter {
public static function doFilter($value) {
return $value !== 3;
}
}
$test = array(1,2,3,4,5);
var_dump(array_filter($test, array('Filter', 'doFilter'))); // 'array(1,2,4,5)'
// -------- or -----------
var_dump(array_filter($test, 'Filter::doFilter')); // As of PHP 5.2.3
Yes, you can. PHP has a "callable" pseudo-type, which is, in fact, either just a string or an array. Several functions (usort comes to mind) accept a parameter of the "callback" type: in fact, they just want a function name, or an object-method pair.
That's right, strings are callable:
$fn = "strlen";
$fn("string"); // returns 6
As mentioned, it's possible to use an array as a callback, too. In that case, the first element has to be an object, and the second argument must be a method name:
$obj = new Foo();
$fn = array($obj, "method");
$fn(); // calls $obj->method()
Previously, you had to use call_user_func to call them, but syntax sugar in recent versions make it possible to perform the call straight on variables.
You can read more on the "callable" documentation page.
No, as far as I know it's not possible to store a reference to a method in PHP. Storing object / class name and a method name in an array works, but it's just an array without any special meaning. You can play with the array as you please, for example:
$ref = [new My_Class(), "x"];
// all is fine here ...
$ref();
// but this also valid, now the 'reference' points to My_Other_Class::x()
// do you expect real reference to behave like this?
$ref[0] = new My_Other_Class();
$ref();
// this is also valid syntax, but it throws fatal error
$ref[0] = 1;
$ref();
// let's assume My_Class::y() is a protected method, this won't work outside My_Class
$ref = [new My_Class(), 'y'];
$ref();
this is prone to error as you loose syntax checking due to storing the method name as string.
you can't pass reliably a reference to a private or a protected method this way (unless you call the reference from a context that already has proper access to the method).
Personally I prefer to use lambdas:
$ref = function() use($my_object) { $my_object->x(); }
If you do this from inside $my_object it gets less clunky thanks to access to $this:
$ref = function() { $this->x(); }
this works with protected / private methods
syntax checking works in IDE (less bugs)
unfortunately it's less concise

Object Oriented Programming -> Operator [duplicate]

This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
Reference - What does this symbol mean in PHP?
So I've been reading through the book PHP Solutions, Dynamic Web Design Made Easy by David Powers. I read through the short section on Object Oriented PHP, and I am having a hard time grasping the idea of the -> operator. Can anyone try to give me a solid explanation on the -> operator in OOP PHP?
Example:
$westcost = new DateTimeZone('America/Los_Angeles');
$now->setTimezone($westcoast);
Also,a more general example:
$someObject->propertyName
The -> operator in PHP refers to either a function or a variable inside a class.
<?php
class Example {
public $variableInClass = "stringContent";
public function functionInClass() {
return "functionReturn";
}
}
$example = new Example();
var_dump($example->variableInClass); //stringContent
var_dump($example->functionInClass()); //functionReturn
?>
Do note that if we're talking about static classes (different purpose), you use :: instead:
<?php
class Example {
public static $variableInClass = "stringContent";
public static function functionInClass() {
return "functionReturn";
}
}
var_dump($example::$variableInClass); //stringContent
var_dump($example::functionInClass()); //functionReturn
?>
$someObject->propertyName can be read as:
return value stored in propertyName from object $someObject
$someObject->methodName() can be read as:
execute methodName from object $someObject
Classes and objects 101:
A class is defined as such:
class MyClass {
public $value1;
public function getValue() {
return $this->value;
}
}
We now defined a class with a single property, and a single function. To use these, we need to create an 'instance' of this object:
$myObject = new MyClass();
To use the property or function, we use the -> operator:
echo $myObject->value1;
echo $myObject->getValue();
Put a little bit more abstractly.. the function getValue is defined in this object. By using the -> operator on an instance of our class, what PHP does is effectively just call the function, just like any other function.. but before it gets called $this is assigned to the current object.
Hope this helps, if not.. I would simply recommend reading about OOP basics.

Php sub-methods

I've used php enough to be quite comfortable with it, but recently I've been looking through some MVC frameworks to try and understand how they work, and I've come across a syntax and data structure which I haven't encountered before:
function view($id)
{
$this->Note->id = $id;
}
What is the ->id section of this code? Is this a sub-method based off it's parent method? If so, how do I go about writing code to create such a structure? (ie. creating the structure from scratch, not using an existing framework like the above example from cakephp).
The following code demonstrates how one could arrive at the structure you described.
<?php
class Note
{
public $id = 42;
}
class MyClass
{
public function __construct() {
// instance of 'Note' as a property of 'MyClass'
$this->Note = new Note();
}
public function test() {
printf("The \$id property in our instance of 'Note' is: %d\n",
$this->Note->id);
}
}
$mc = new MyClass();
$mc->test();
?>
Note is a property of $this and it's (current) value is an object with a property named id which gets assigned the value of $id.
If id was a method of the Note object, the line would read $this->Note->id($id);.
Another way to think about the construct is considering
$this->Note->id = $id;
similar to
$this["Note"]["id"] = $id;
Which would actually be equivalent if both objects ($this and subobject Note) were based on ArrayAccess.

Categories