note 108690 added to language.operators.comparison

From: Date: Thu, 17 May 2012 21:20:21 +0000
Subject: note 108690 added to language.operators.comparison
Groups: php.notes 
Request: Send a blank email to php-notes+get-188045@lists.php.net to get a copy of this message
COMPARING PHP OBJECTS (compound type) We have seen that PHP does a lot of type-juggling on its own -- which can wreak havoc in unexpected ways -- but it is still up to us to produce code that is clear, maintainable AND follows the rules we want to follow. When creating a PHP Object, it is sometimes unclear what makes two of them the same. But the good part is that we can say what is equal and what is not equal. For example, let's say we have a Student class that includes an equals() method which defines what is equal for this type of object. <?php #Student.php class Student { /* * These variables are protected to prevent outside code * from tampering with them. */ protected $student_id; protected $student_name; public function __construct($id, $name) { $this->student_id = (int)$id; // cast to integer here $this->student_name = (string)$name; // cast to string here } /* * This function requires an instance of type Student and * only evaluates two integers that we set in __construct(). */ public function equals(Student $student) { return ($this->getId() == $student->getId()); } public function getId() { return $this->student_id; } public function getName() { return $this->student_name; } public function __toString() { return 'Student [id=' . $this->getId() . ', name=' . $this->getName() . ']'; } } ?> With this class, the protected variables cannot be tampered with by outside code. Also, the __construct() function casts the variables to the PHP primitives WE WANT, while the equals(Student $student) function, requires an argument of type Student -- which eliminates the need for an IDENTITY '===' check AND prevents any other data types from coming in. One other note: notice how the equals() function only evaluates the $student_id, this allows for two students to have the same name -- which is totally possible. Here's a short example -- we'll do it correctly AND try to screw it up! <?php require('Student.php'); $s1 = new Student(122, 'John Doe'); $s2 = new Student(344, 'John Doe'); echo $s1 . '<br>'; // Student [id=122, name=John Doe] echo $s2 . '<br>'; // Student [id=344, name=John Doe] # Check for equality the CORRECT way... echo ($s1->equals($s2) ? 'EQUAL' : 'NOT EQUAL'); // NOT EQUAL # Check for equality by HACKING the known value of $student_id... echo ($s1->equals(122) ? 'EQUAL' : 'NOT EQUAL'); // Catchable fatal error: Argument 1 passed to Student::equals() must be an instance of Student, integer given... etc, etc. ?> See what I mean by writing code that follows OUR RULES? The Student class does the kind of type-juggling we want (and when we want it done) -- NOT when, where, or why PHP does it (not that there's anything wrong with it). ---- Server IP: 69.147.83.197 Probable Submitter: 69.19.176.197 ---- Manual Page -- http://www.php.net/manual/en/language.operators.comparison.php Edit -- https://master.php.net/note/edit/108690 Del: integrated -- https://master.php.net/note/delete/108690/integrated Del: useless -- https://master.php.net/note/delete/108690/useless Del: bad code -- https://master.php.net/note/delete/108690/bad+code Del: spam -- https://master.php.net/note/delete/108690/spam Del: non-english -- https://master.php.net/note/delete/108690/non-english Del: in docs -- https://master.php.net/note/delete/108690/in+docs Del: other reasons-- https://master.php.net/note/delete/108690 Reject -- https://master.php.net/note/reject/108690 Search -- https://master.php.net/manage/user-notes.php

« previous php.notes (#188045) next »