|
 |
Every class definition begins with the keyword class, followed by a class
name, which can be any name that isn't a reserved
word in PHP. Followed by a pair of curly braces, of
which contains the definition of the classes members and methods. A
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, but can be another object, if the method is called
statically from the context
of a secondary object). This is illustrated in the following example:
Пример 19-1. $this variable in object-oriented language
<?php
class A
{
function foo()
{
if (isset($this)) {
echo '$this is defined (';
echo get_class($this);
echo ")\n";
} else {
echo "\$this is not defined.\n";
}
}
}
class B
{
function bar()
{
A::foo();
}
}
$a = new A();
$a->foo();
A::foo();
$b = new B();
$b->bar();
B::bar();
?>
|
Результат выполнения данного примера: $this is defined (a)
$this is not defined.
$this is defined (b)
$this is not defined. |
|
Пример 19-2. Simple Class definition
<?php
class SimpleClass
{
public $var = 'a default value';
public function displayVar() {
echo $this->var;
}
}
?>
|
|
To create an instance of an object, a new object must be created and
assigned to a variable. An object will always be assigned when
creating a new object unless the object has a
constructor defined that throws an
exception on error.
Пример 19-3. Creating an instance
<?php
$instance = new SimpleClass();
?>
|
|
When assigning an already created instance of an object to a new variable, the new variable
will access the same instance as the object that was assigned. This
behaviour is the same when passing instances to a function. A new instance
of an already created object can be made by
cloning it.
Пример 19-4. Object Assignment
<?php
$assigned = $instance;
$reference =& $instance;
$instance->var = '$assigned will have this value';
$instance = null; var_dump($instance);
var_dump($reference);
var_dump($assigned);
?>
|
Результат выполнения данного примера: NULL
NULL
object(SimpleClass)#1 (1) {
["var"]=>
string(30) "$assigned will have this value"
} |
|
A class can inherit methods and members of another class by using the
extends keyword in the declaration. It is not possible to extend multiple
classes, a class can only inherit one base class.
The inherited methods and members can be overridden, unless the parent
class has defined a method as final,
by redeclaring them within the same name defined in the parent class.
It is possible to access the overrided method or members by
referencing them with parent::
Пример 19-5. Simple Class Inherintance
<?php
class ExtendClass extends SimpleClass
{
function displayVar()
{
echo "Extending class\n";
parent::displayVar();
}
}
$extended = new ExtendClass();
$extended->displayVar();
?>
|
Результат выполнения данного примера: Extending class
a default value |
|
The Basics
edwardzyang at thewritingpot dot com
13-Apr-2006 12:47
I read the first few comments about references versus assignment on objects, and I still couldn't get it. I'm going to talk about it in terms of practical usage, not the tomfoolery occuring behind the scenes. No talk of memory pointers and the like.
<?php
class Mushroom
{
public $size;
public function __construct($size) {
$this->size = $size;
}
}
$mushroom = new Mushroom(1);
$assigned_shroom = $mushroom;
$reference_shroom =& $mushroom;
?>
Assignments and references, when it comes down to calling functions and modifying member variables, don't make ANY difference at all.
<?php
$mushroom->size = 5;
?>
The only deviation of behavior is when you assign totally new contents to a variable. Usually, this never happens unless you're doing some strange reflection or injection.
<?php
$mushroom = 5;
?>
<?php
$reference_shroom = 5;
?>
<?php
$assigned_shroom = 5;
?>
The same would apply for any object type.
Once again, I reiterate, there's no need to overwrite variables and open this can of worms: just make a new variable and be done with it. As long as you don't overwrite variables, it doesn't matter whether or not you use references or assignments (unless you're planning for PHP4 compatibility).
ben AT chemica.co.uk
01-Feb-2006 05:40
PHP classes helpfully allow you to define member variables on the fly. On top of that, dynamic variables mean you can create them by name from strings.
This means you can ape the 'Ruby On Rails' view system - or replace heavyweight templating systems like Smarty - with very little code:
view.class.php:
<?
class View
{
public function AddVariables($aVariables){
foreach($aVariables as $name => $value){
$this->AddVariable($name, $value);
}
}
public function AddVariable($name, $value){
$this->$name = $value; }
public function Render($template){
include($template . ".php");
}
protected function AddParagraph($strText){
echo("<p>" . $strText . "</p>");
}
protected function AddOptions($aOptions, $strSelected){
foreach($aOptions as $value => $text){
echo "<option value='" . $value . "'";
if($value==$strSelected){echo " selected";}
echo ">" . $text . "</option>\n";
}
}
}
$v = new View();
$v->AddVariables(array("peach"=>"fruit", "carrot"=>"vegetable"));
$v->AddVariables(array("options" => array("1"=>"Jan", "2"=>"Feb", "3"=>"March")));
$v->AddVariable("bodytext", "Some content goes here");
$v->Render("test");
?>
test.php:
<html>
<body>
<p>A peach is a <? echo $this->peach; ?>.</p>
<p>A carrot is a <? echo $this->carrot; ?>.<p>
<form action="#" method="GET">
<select id="test">
<? $this->AddOptions($this->options, 2); ?>
</select>
</form>
<? $this->AddParagraph($this->bodytext); ?>
</body>
</html>
This means you can unleash the awesome power of PHP on your templates, allowing all kinds of cool tricks, while ensuring you're not mixing up your display and business code. You only have access to the variables you pass in there yourself. Oh, and the library of markup rendering member functions you'll create. In PHP.
You can re-use templates - just use the same variables with a different page.
You can swap in different mark-up languages programatically, so you could make versions that spit out HTML, XHTML, WML, and XML for SOAP interfaces.
It's entirely extensible. Either write in more PHP member functions to automate view-based tasks, or derive new classes and extend the functionality that way. (Perfect for your proprietary XML language helper functions - they really don't belong in the same class that's generating XHTML.)
The best part is that it's all PHP, so you don't have to learn a new language (as you would do with Smarty - or if you wanted to switch over to Ruby on Rails.)
Hope someone finds it useful. If anyone makes any improvements, corrections etc. I'd love to see them. :)
You'll need a recent version of PHP5 to run it - some earlier versions gave strange scoping errors with the use of $this. I know that build date 'Jan 11 2006 16:35:21' works.
mrich at runbox dot removethis dot com
06-Dec-2005 01:45
PHP 4.3.10:
<?php
class foo {
var $what;
function foo($newWhat = 'foo') {
$this->what = $newWhat;
}
function bar() {
print "<p>I'm a ".$this->what."</p>\n";
}
}
$var = 'foo';
$obj = new $var;
$obj->bar();
$obj = new $var();
$obj->bar();
$obj = new $var('bar');
$obj->bar();
?>
npugh at tacc dot utah dot edu
29-Nov-2005 02:10
Note that a function defined in the parent class may not access a private member of a child class.
<?php
class A
{
public function foo() { echo $this->x; }
}
class B extends A
{
protected $x = "class B's member";
}
class C extends A
{
private $x = "class C's member";
}
$b = new B();
$b->foo();
$c = new C();
$c->foo();
?>
In the above example, if you don't want to duplicate function foo() in all of the child classes you would have to make each member foo() operates on protected or public. Effectively breaking encapsulation to in order to implement polymorphism.
PHP at Rulez dot com
10-Oct-2005 10:35
Check this!!!
<?php
class foo{
function bar() {
return $this;
}
function hello() {
echo "Hello";
}
}
$foo = new foo();
$foo->bar()->bar()->bar()->bar()->hello();
?>
Haaa! Rulezzz!
chris dot good at NOSPAM dot geac dot com
12-Sep-2005 09:32
Note that Class names seem to be case-insensitive in php 5.
eg
class abc
{
..
{
class def extends ABC
{
..
}
works fine.
jerry
12-Jun-2005 02:30
Note the little correction on graced's notes below:
Your explanation looks correct about how instances created and destroyed, just wanted to correct some errors in your code below. But Thank you greatly for explaining that I appreciate it.
<?php
$obj1 = new stdclass();
var_dump($obj1); $obj1 = new stdclass();
var_dump($obj1); $obj1 = new stdclass(); var_dump($obj1);
$obj2 = $obj1; $obj1 = new stdclass(); var_dump($obj1);
$obj1 = new stdclass(); var_dump($obj1);
?>
Output:
object(stdClass)#1 (0) {
}
object(stdClass)#2 (0) {
}
object(stdClass)#1 (0) {
}
object(stdClass)#2 (0) {
}
object(stdClass)#3 (0) {
}
rasmus at nospaam dot flajm dot com
05-Apr-2005 03:22
A very good (in my opinion) change in PHP5 is that objects are always passed by reference. In PHP4 they where passed by value, which cased a copy to be made for every call. (as long as you didn't use "&" of cause)
This example illustrates pass-by-reference, as the name changes in the same object, passed around two different ways:
<?php
class Mother {
private $obj = null;
public function setChild($o) {
$this->obj = $o;
}
public function getChild() {
return $this->obj;
}
}
class Child {
private $name = 'noname';
public function setName($string) {
$this->name = $string;
}
public function getName() {
return $this->name;
}
}
$mom = new Mother();
$frasse = new Child();
$frasse->setName('Johan');
$mom->setChild($frasse);
$frasse->setName('Frans');
print $frasse->getName() . "\n";
print $mom->getChild()->getName() . "\n";
?>
This will print:
Frans
Frans
In PHP4, this would print:
Frans
Johan
graced at monroe dot NOSPAM dot wednet dot edu
29-Mar-2005 10:46
In reponse to jerry's comment: "If you instantiate a class and assign it to a variable over and over again, php will start saving instances #1 and #2 in memory but will stop at these"...
This is because after assigning the new object to the variable, there is no longer anything referencing the old object so it is destroyed. If there WAS another reference, say you assigned another variable to the first variable before setting the first to a new class, it'd be preserved.
In reality, this really makes no difference to the programmer, just thought an explanation was in order.
<?php
$obj1 = new stdclass();
var_dump($obj1); $obj1 = new stdclass();
var_dump($obj1); $obj1 = new stdclass(); var_dump($obj1);
$obj2 = $obj1; $obj1 = new stdclass(); var_dump($obj1);
$obj1 = new stdclass(); ?>
tigr at mail15 dot com
01-Mar-2005 04:08
Objects are not being passed by reference as varables do. Let me try to explain:
Variable passing by reference means that two variables are being binded together, so that changing one variable leads to changes in the other. In fact, there is only one variable.
Object passing by reference is a bit different. It means that not the object itself is being passed (that would lead to copying it and all evil), but only reference to the object is being passed. Now, both VARIABLES point to the same object, BUT they DO NOT point to each other. There are TWO DIFFERENT variables. This means that if you change one VARIABLE, second one would still point to the same object.
So, adding reference operator still has some sense. Here is an example:
<?php
class sampleClass {
public $id;
public function __construct($id) { $this->id=$id; }
}
$object1 = new sampleClass(1);
$object2 = $object1;
echo $object1->id; echo $object2->id; $object2 = new sampleClass(2);
echo $object1->id; echo $object2->id; $object3 = &$object1; $object3 = new sampleClass(3);
echo $object1->id; echo $object2->id; echo $object3->id; ?>
jerry
12-Jan-2005 10:41
If you instantiate a class and assign it to a variable over and over again, php will start saving instances #1 and #2 in memory but will stop at these, and will not save more than those instances(ie. #3, #4, #5, #6...). Instead it will toggle between #1 and #2.
<?php
$obj1 = new stdclass();
var_dump($obj1);
$obj1 = new stdclass();
var_dump($obj1);
$obj1 = new stdclass();
var_dump($obj1);
$obj1 = new stdclass();
var_dump($obj1);
$obj1 = new stdclass();
var_dump($obj1);
$obj1 = new stdclass();
var_dump($obj1);
$obj1 = new stdclass();
var_dump($obj1);
?>
Richard (php at tsg1985 dot com)
12-Dec-2004 08:36
"Actually, the new variable will access a COPY of the instance and not the SAME instance. This is shown by the example: var_dump($assigned) was not NULLified because a COPY of the instance was assigned to $assigned..."
This is actually incorrect. However, it is explained really poorly in the article.
$instance = new SimpleClass();
This creates the new SimpleClass Object location in the memory. (This spot in memory stores all of the variable and the code to execute.)Then, it points the variable $instance to that location in the memory.
$assigned =$instance;
This takes the location that $instance is pointed to and points the variable $assigned to it as well.
$reference =& $instance;
This line of code points $refrence to the memory spot which contains the location of the SimpleClass object, not the object!
$instance->var = '$assigned will have this value';
This changes the values stored in SimpleClass Object's memory. Since $assigned points to this location as well, $assinged>var is the same value.
$instance = null;
This tells instance to point at nothing. So, it breaks its link to the SimpleClass object. $refrence points to $instance still, but since $instance points to nothing $refrence will also point to nothing.
I know this is kind of tough to understand, so I made an animated gif showing the steps.
http://www.prism.gatech.edu/~gtg624r/Code_Explenation.gif
| |