php编程 之 php基础三

1,php里的while循环

循环执行代码块指定的次数,或者当指定的条件为真时循环执行代码块。

while实例:

<html>
<body>

<?php
$i=1;
while($i<=5)    //注意,此处不支持简写。
{
    echo "The number is " . $i . "<br>";
    $i++;
}
?>

</body>
</html>

do ...while...实例:

do
{
    要执行的代码;
}
while (条件);

2,for循环

语法:

for (初始值; 条件; 增量)
{
    要执行的代码;
}

只循环数字:

<?php
for ($i=1; $i<=5; $i++)
{
    echo "The number is " . $i . "<br>";
}
?>

循环数组:

<?php
$x=array("one","two","three");
foreach ($x as $value)    //键值对的键是$x,值是$value
{
    echo $value . "<br>";
}
?>

3,函数

PHP 的真正威力源自于它的函数。在 PHP 中,提供了超过 1000 个内建的函数。

php内建函数手册:http://www.runoob.com/php/php-ref-array.html

创建:

<?php
function functionName()    //名字最好具有提示性,函数名不能以数字开头
{
    // 要执行的代码
}
?>

带参数:

<?php
function writeName($fname)
{
    echo $fname . “how are u?”;
}

writeName("Kai Jim");    //返回Kai Jim how are u?
?>

带返回值的函数:

<?php
function add($x,$y)
{
    $total=$x+$y;
    return $total;   //return
}

echo "1 + 16 = " . add(1,16);
?>

4 魔术常量

PHP 向它运行的任何脚本提供了大量的预定义常量。不大好解释,但是它们的数据类型是常量,但是具体值要看情况而定。

__LINE__:当前行的行号

<?php
echo ‘这是第 " ‘  . __LINE__ . ‘ " 行‘;    //返回2
?>

__FILE__:文件的完整路径和文件名。如果用在被包含文件中,则返回被包含的文件名。

<?php
echo ‘该文件位于 " ‘  . __FILE__ . ‘ " ‘;
?>

__DIR__:文件所在的目录。如果用在被包括文件中,则返回被包括的文件所在的目录。等于dirname(__FILE__)

<?php
echo ‘该文件位于 " ‘  . __DIR__ . ‘ " ‘;    //返回"E:\wamp\www\test"
?>

__FUNCTION__:本常量返回该函数被定义时的名字(区分大小写)

<?php
function test() {
    echo  ‘函数名为:‘ . __FUNCTION__ ;
}
test();
?>    //返回test

__CLASS__:返回该类再被定义时候的名字

<?php
class test {
    function _print() {
        echo ‘类名为:‘  . __CLASS__ . "<br>";    //返回test
        echo  ‘函数名为:‘ . __FUNCTION__ ;    //返回_print
    }
}
$t = new test();
$t->_print();
?>

__NAMESPACE__

当前命名空间的名称(区分大小写)。

<?php
namespace MyProject;

echo ‘命名空间为:"‘, __NAMESPACE__, ‘"‘; // 输出 "MyProject"
?>

__METHOD__:类的方法名,返回该方法被定义时候的名字。

<?php
function test() {
    echo  ‘函数名为:‘ . __METHOD__ ;
}
test();
?>

__TRAIT__:Trait是为类似PHP的单继承语言而准备的一种代码复用机制。

php从以前到现在一直都是单继承的语言,无法同时从两个基类中继承属性和方法,为了解决这个问题,php出了Trait这个特性

用法:通过在类中使用use 关键字,声明要组合的Trait名称,具体的Trait的声明使用Trait关键词,Trait不能实例化

<?php
trait Dog{    //定义一个trait类,方法和class差不多,但是它不能被实例化
    public $name="dog";    //公有属性是name
    public function bark(){    //公有方法
        echo "This is dog";
    }
}
class Animal{
    public function eat(){
        echo "This is animal eat";
    }
}
class Cat extends Animal{    //class 子类 extends 父类
    use Dog;    //trait类继承的写法,这样Cat类也会继承Dog类
    public function drive(){
        echo "This is cat drive";
    }
}
$cat = new Cat();    //实例化cat
$cat->drive();    //返回this is cat drive
echo "<br/>";
$cat->eat();    //返回this is animal eat
echo "<br/>";
$cat->bark();    //返回this is dog
?>

由于trait和class的多继承有可能会造成父类子类属性和方法的冲突,所以我们再来个例子看一下覆盖问题:

<?php
class Base {    //基类,拥有sayHello方法
    public function sayHello() {
        echo ‘Hello ‘;
    }
}

trait SayWorld {    //trait类,也拥有sayhello方法
    public function sayHello() {
        parent::sayHello();    //parent::    的意思是调用父类但是不仅限于父类的方法,也就是会继承上一个sayHello的方法,也就是print hello
        echo ‘World!‘;
    }
}

class MyHelloWorld extends Base {
    use SayWorld;    //继承的是trait SayWorld
}

$o = new MyHelloWorld();
$o->sayHello();    //返回hello world !
?>

5 命名空间:

https://blog.csdn.net/ss22_xiha/article/details/52694279这个教程还不错

感觉有点想python中的全局变量和局部变量。只不过明确地写出来了而已。

PHP 命名空间可以解决以下两类问题:

  1. 用户编写的代码与PHP内部的类/函数/常量或第三方类/函数/常量之间的名字冲突。
  2. 为很长的标识符名称(通常是为了缓解第一类问题而定义的)创建一个别名(或简短)的名称,提高源代码的可读性。

如何定义命名空间:

命名空间通过关键字namespace 来声明。如果你想使用命名空间,它必须在其它所有代码之前声明命名空间。语法格式如下;

<?php    //一个文件中拥有多个命名空间//不加大括号也行,不过加上比较严谨
declare(encoding=‘UTF-8‘);

//在声明命名空间之前唯一合法的代码是用于定义源文件编码方式的 declare 语句。所有非 PHP 代码包括空白符都不能出现在命名空间的声明之前。即使是<html>也不行。好霸道啊,不过对这一点还是感觉不是特别理解
namespace MyProject {
    //一堆代码
}

namespace AnotherProject {
    //一堆代码
}
?>
<?php
//全局代码和命名空间的代码写在一块
namespace MyProject {    //这个是命名空间
    //一堆代码
}

namespace { // 这个是全局代码,注意全局代码的写法,namespace关键字后面不加任何东西,然后大括号括起来
    //一堆代码
}
?>

 子命名空间:

与目录和文件的关系很像,PHP 命名空间也允许指定层次化的命名空间的名称。因此,命名空间的名字可以使用分层次的方式定义。

<?php
namespace MyProject\Sub\Level;  //声明分层次的单个命名空间,是反斜杠哦:
//一堆代码

?>

如何使用命名空间:

PHP 命名空间中的元素使用同样的原理。例如,类名可以通过三种方式引用:

  1. 非限定名称,或不包含前缀的类名称,例如 $a=new foo(); 或 foo::staticmethod();。如果当前命名空间是currentnamespace,foo 将被解析为 currentnamespace\foo。如果使用 foo 的代码是全局的,不包含在任何命名空间中的代码,则 foo 会被解析为foo。 警告:如果命名空间中的函数或常量未定义,则该非限定的函数名称或常量名称会被解析为全局函数名称或常量名称。详情参见 使用命名空间:后备全局函数名称/常量名称
  2. 限定名称,或包含前缀的名称,例如 $a = new subnamespace\foo(); 或 subnamespace\foo::staticmethod();。如果当前的命名空间是 currentnamespace,则 foo 会被解析为 currentnamespace\subnamespace\foo。如果使用 foo 的代码是全局的,不包含在任何命名空间中的代码,foo 会被解析为subnamespace\foo
  3. 完全限定名称,或包含了全局前缀操作符的名称,例如, $a = new \currentnamespace\foo(); 或\currentnamespace\foo::staticmethod();。在这种情况下,foo 总是被解析为代码中的文字名(literal name)currentnamespace\foo

基本意思就是,如果你没指定命名空间那就默认为当前的命名空间,全局的也是这样的。为了防止和别的名称空间里的变量重名,你也可以指定命名空间的“相对路径”或者“绝对路径”

/* 非限定名称 */
foo(); // 解析为函数 Foo\Bar\foo
foo::staticmethod(); // 解析为类 Foo\Bar\foo ,方法为 staticmethod,双冒号表示调用某类下的方法
echo FOO; // 解析为常量 Foo\Bar\FOO

/* 限定名称 */
subnamespace\foo(); // 解析为函数 Foo\Bar\subnamespace\foo
subnamespace\foo::staticmethod(); // 解析为类 Foo\Bar\subnamespace\foo,
                                  // 以及类的方法 staticmethod
echo subnamespace\FOO; // 解析为常量 Foo\Bar\subnamespace\FOO

/* 完全限定名称 */
\Foo\Bar\foo(); // 解析为函数 Foo\Bar\foo
\Foo\Bar\foo::staticmethod(); // 解析为类 Foo\Bar\foo, 以及类的方法 staticmethod
echo \Foo\Bar\FOO; // 解析为常量 Foo\Bar\FOO

命名空间的导入

允许通过别名引用或导入外部的完全限定名称,是命名空间的一个重要特征。这有点类似于在类 unix 文件系统中可以创建对其它的文件或目录的符号连接。

所有支持命名空间的PHP版本支持三种别名或导入方式:为类名称使用别名、为接口使用别名或为命名空间名称使用别名。PHP 5.6开始允许导入函数或常量或者为它们设置别名

__NAMESPACE__

常量__NAMESPACE__的值是包含当前命名空间名称的字符串。在全局的,不包括在任何命名空间中的代码,它包含一个空的字符串。

<?php
namespace MyProject;
echo ‘"‘, __NAMESPACE__, ‘"‘; // 输出 "MyProject"
?>

关键字 namespace 可用来显式访问当前命名空间或子命名空间中的元素。

不是很懂,留后

使用名称空间:

PHP 命名空间支持 有两种使用别名或导入方式:为类名称使用别名,或为命名空间名称使用别名。

在PHP中,别名是通过操作符 use 来实现的. 下面是一个使用所有可能的三种导入方式的例子:

//使用use关键字导入,并且为这个名称空间取个别名:
<?php
namespace foo;
use My\Full\Classname as Another;    //我要用xxx命名空间,别名是another

// 下面的例子与 use My\Full\NSname as NSname 相同
use My\Full\NSname;

// 导入一个全局类
use \ArrayObject;

$obj = new namespace\Another; // 实例化 foo\Another 对象
$obj = new Another; // 实例化 My\Full\Classname 对象
NSname\subns\func(); // 调用函数 My\Full\NSname\subns\func
$a = new ArrayObject(array(1)); // 实例化 ArrayObject 对象
// 如果不使用 "use \ArrayObject" ,则实例化一个 foo\ArrayObject 对象
?>

//一行多个use语句并列
<?php
use My\Full\Classname as Another, My\Full\NSname;

$obj = new Another; // 实例化 My\Full\Classname 对象
NSname\subns\func(); // 调用函数 My\Full\NSname\subns\func
?>

//用另一个动态名称代替:
<?php
use My\Full\Classname as Another, My\Full\NSname;

$obj = new Another; // 实例化一个 My\Full\Classname 对象
$a = ‘Another‘;
$obj = new $a;      // 实际化一个 Another 对象
?>

使用命名空间的注意事项:

在访问系统内部或不包含在命名空间中的类名称时,必须使用完全限定名称;

对于函数和常量来说,如果当前命名空间中不存在该函数或常量,PHP 会退而使用全局空间中的函数或常量;

全局空间:

如果没有定义任何命名空间,所有的类与函数的定义都是在全局空间,我们在名称前加上前缀 \ 表示该名称是全局空间中的名称

<?php
namespace A\B\C;
$f = \fopen(...); // 调用全局的fopen函数
     return $f;
?>

命名空间的顺序:

//不说了,直接上实例
<?php
namespace A;
use B\D, C\E as F;

// 函数调用

foo();      // 首先尝试调用定义在命名空间"A"中的函数foo()
            // 再尝试调用全局函数 "foo"

\foo();     // 调用全局空间函数 "foo" 

my\foo();   // 调用定义在命名空间"A\my"中函数 "foo" 

F();        // 首先尝试调用定义在命名空间"A"中的函数 "F"
            // 再尝试调用全局函数 "F"

// 类引用

new B();    // 创建命名空间 "A" 中定义的类 "B" 的一个对象
            // 如果未找到,则尝试自动装载类 "A\B"

new D();    // 使用导入规则,创建命名空间 "B" 中定义的类 "D" 的一个对象
            // 如果未找到,则尝试自动装载类 "B\D"

new F();    // 使用导入规则,创建命名空间 "C" 中定义的类 "E" 的一个对象
            // 如果未找到,则尝试自动装载类 "C\E"

new \B();   // 创建定义在全局空间中的类 "B" 的一个对象
            // 如果未发现,则尝试自动装载类 "B"

new \D();   // 创建定义在全局空间中的类 "D" 的一个对象
            // 如果未发现,则尝试自动装载类 "D"

new \F();   // 创建定义在全局空间中的类 "F" 的一个对象
            // 如果未发现,则尝试自动装载类 "F"

// 调用另一个命名空间中的静态方法或命名空间函数

B\foo();    // 调用命名空间 "A\B" 中函数 "foo"

B::foo();   // 调用命名空间 "A" 中定义的类 "B" 的 "foo" 方法
            // 如果未找到类 "A\B" ,则尝试自动装载类 "A\B"

D::foo();   // 使用导入规则,调用命名空间 "B" 中定义的类 "D" 的 "foo" 方法
            // 如果类 "B\D" 未找到,则尝试自动装载类 "B\D"

\B\foo();   // 调用命名空间 "B" 中的函数 "foo" 

\B::foo();  // 调用全局空间中的类 "B" 的 "foo" 方法
            // 如果类 "B" 未找到,则尝试自动装载类 "B"

// 当前命名空间中的静态方法或函数

A\B::foo();   // 调用命名空间 "A\A" 中定义的类 "B" 的 "foo" 方法
              // 如果类 "A\A\B" 未找到,则尝试自动装载类 "A\A\B"

\A\B::foo();  // 调用命名空间 "A" 中定义的类 "B" 的 "foo" 方法
              // 如果类 "A\B" 未找到,则尝试自动装载类 "A\B"
?>

6,面向对象

面向对象内容

  •  ? 定义了一件事物的抽象特点。类的定义包含了数据的形式以及对数据的操作。
  • 对象 ? 是类的实例。
  • 成员变量 ? 定义在类内部的变量。该变量的值对外是不可见的,但是可以通过成员函数访问,在类被实例化为对象后,该变量即可称为对象的属性。
  • 成员函数 ? 定义在类的内部,可用于访问对象的数据。
  • 继承 ? 继承性是子类自动共享父类数据结构和方法的机制,这是类之间的一种关系。在定义和实现一个类的时候,可以在一个已经存在的类的基础之上来进行,把这个已经存在的类所定义的内容作为自己的内容,并加入若干新的内容。
  • 父类 ? 一个类被其他类继承,可将该类称为父类,或基类,或超类。
  • 子类 ? 一个类继承其他类称为子类,也可称为派生类。
  • 多态 ? 多态性是指相同的函数或方法可作用于多种类型的对象上并获得不同的结果。不同的对象,收到同一消息可以产生不同的结果,这种现象称为多态性。
  • 重载 ? 简单说,就是函数或者方法有同样的名称,但是参数列表不相同的情形,这样的同名不同参数的函数或者方法之间,互相称之为重载函数或者方法。
  • 抽象性 ? 抽象性是指将具有一致的数据结构(属性)和行为(操作)的对象抽象成类。一个类就是这样一种抽象,它反映了与应用有关的重要性质,而忽略其他一些无关内容。任何类的划分都是主观的,但必须与具体的应用有关。
  • 封装 ? 封装是指将现实世界中存在的某个客体的属性与行为绑定在一起,并放置在一个逻辑单元内。
  • 构造函数 ? 主要用来在创建对象时初始化对象, 即为对象成员变量赋初始值,总与new运算符一起使用在创建对象的语句中。
  • 析构函数 ? 析构函数(destructor) 与构造函数相反,当对象结束其生命周期时(例如对象所在的函数已调用完毕),系统自动执行析构函数。析构函数往往用来做"清理善后" 的工作(例如在建立对象时用new开辟了一片内存空间,应在退出前在析构函数中用delete释放)。

定义类的语法:

<?php
class phpClass {
  var $var1;    //类的变量使用 var 来声明, 变量也可以初始化值。
  var $var2 = "constant string";

  function myfunc ($arg1, $arg2) {    //函数定义类似 PHP 函数的定义,但函数只能通过该类及其实例化的对象访问。

     [..]
  }
  [..]
}
?>

实例:

<?php
class Site {
  /* 成员变量 */
  var $url;
  var $title;

  /* 成员函数 */
  function setUrl($par){
     $this->url = $par;
  }

  function getUrl(){
     echo $this->url . PHP_EOL;    //PHP_EOL表示换行
  }

  function setTitle($par){
     $this->title = $par;
  }

  function getTitle(){
     echo $this->title . PHP_EOL;
  }
}
?>

php使用new来创建实例:

如何调用呢?记住php类中调用实例的属性或者方法的时候,用“->”

$google = new Site; 

// 调用成员函数,设置标题和URL
$google->setTitle( "Google 搜索" ); 

$google->setUrl( ‘www.google.com‘ ); 

// 调用成员函数,获取标题和URL
$google->getTitle(); 

$google->getUrl()

php构造函数:(这个比较重要了)

<?php
class Site {
  /* 成员变量 */
  var $url;
  var $title;

  function __construct( $par1, $par2 ) {    //这个是构造函数,感觉还是和js不一样,php是在class里面用构造函数,纯粹为了初始化的时候格式比较省事把,个人觉得,总觉得php的类是pytho向js的过度形式
    $this->url = $par1;
    $this->title = $par2;
  }
  /* 成员函数 */
  function setUrl($par){
     $this->url = $par;
  }

  function getUrl(){
     echo $this->url . PHP_EOL;
  }

  function setTitle($par){
     $this->title = $par;
  }

  function getTitle(){
     echo $this->title . PHP_EOL;
  }
}

$runoob = new Site(‘www.runoob.com‘, ‘菜鸟教程‘);

// 调用成员函数,获取标题和URL
$runoob->getTitle();

?>

析构函数

析构函数(destructor) 与构造函数相反,当对象结束其生命周期时(例如对象所在的函数已调用完毕),系统自动执行析构函数。

<?php
class MyDestructableClass {
   function __construct() {
       print "构造函数\n";
       $this->name = "MyDestructableClass";
   }

   function __destruct() {
       print "销毁 " . $this->name . "\n";    //这个是析构函数,很想python中的魔法方法,__del__这种的
   }
}

$obj = new MyDestructableClass();
?>

继承

class Child extends Parent {    //class子类extends父类
//代码
}

如果父类的属性和方法不能满足子类的需求,那子类可以选择重写这个方法。

访问控制

PHP 对属性或方法的访问控制,是通过在前面添加关键字 public(公有),protected(受保护)或 private(私有)来实现的。

  • public(公有):公有的类成员可以在任何地方被访问。var定义的类属性会被当成公有
  • protected(受保护):受保护的类成员则可以被其自身以及其子类和父类访问。
  • private(私有):私有的类成员则只能被其定义所在的类访问。

实例,我们来具体看一下访问是如何被控制的:

class MyClass
{
    public $public = ‘Public‘;
    protected $protected = ‘Protected‘;
    private $private = ‘Private‘;

    function printHello()
    {
        echo $this->public;
        echo $this->protected;
        echo $this->private;
    }
}

$obj = new MyClass();
echo $obj->public; // 这行能被正常执行
echo $obj->protected; // 这行会产生一个致命错误,说明实例不能访问类的protected属性
echo $obj->private; // 这行也会产生一个致命错误,说明实例不能访问类的private属性
$obj->printHello(); // 输出 Public、Protected 和 Private,说明类的方法本身可以访问自己的各种属性

接上一个程序

class MyClass2 extends MyClass    //新建一个子类
{
    // 子类中可以对 public 和 protected 进行重定义,但 private 而不能
    protected $protected = ‘Protected2‘;

    function printHello()
    {
        echo $this->public;
        echo $this->protected;
        echo $this->private;
    }
}

$obj2 = new MyClass2();
echo $obj2->public; // 这行能被正常执行
echo $obj2->private; // 未定义 private,说明private属性不但不能被实例访问,还不能被继承
echo $obj2->protected; // 这行会产生一个致命错误,虽然产生了错误,但是并不能说明没有继承或者重写,实际上它就是已经被继承了而且被重写了,只是不能被实例访问而已
$obj2->printHello(); // 输出 Public、Protected2 和 Undefined

备注方法的访问控制和属性的访问控制是基本一样的,

实例都不可以访问受保护的或者私有的方法,私有方法不可以被子类继承。

接口:

使用接口(interface),可以指定某个类必须实现哪些方法,但不需要定义这些方法的具体内容。

接口是通过 interface 关键字来定义的,就像定义一个标准的类一样,但其中定义所有的方法都是空的。

接口中定义的所有方法都必须是公有,这是接口的特性。

要实现一个接口,使用 implements 操作符。类中必须实现接口中定义的所有方法,否则会报一个致命错误。类可以实现多个接口,用逗号来分隔多个接口的名称。

<?php

// 声明一个‘iTemplate‘接口
interface iTemplate
{
    public function setVariable($name, $var);
    public function getHtml($template);
}

// 实现接口
class Template implements iTemplate
{
    private $vars = array();

    public function setVariable($name, $var)
    {
        $this->vars[$name] = $var;
    }

    public function getHtml($template)
    {
        foreach($this->vars as $name => $value) {
            $template = str_replace(‘{‘ . $name . ‘}‘, $value, $template);
        }

        return $template;
    }
}

按照我的理解,接口更像是一个硬性规定,规定你类里必须有接口规定的内容,少一个不行,至于你某个接口内容的算法,你随意,我不care。

常量:

可以把在类中始终保持不变的值定义为常量。在定义和使用常量的时候不需要使用 $ 符号。

常量的值必须是一个定值,不能是变量,类属性,数学运算的结果或函数调用。

class MyClass
{
    const constant = ‘常量值‘;    //这样写

    function showConstant() {
        echo  self::constant . PHP_EOL;
    }
}

抽象类:

和接口有点像,

任何一个类,如果它里面至少有一个方法是被声明为抽象的,那么这个类就必须被声明为抽象的。

定义为抽象的类不能被实例化。

被定义为抽象的方法只是声明了其调用方式(参数),不能定义其具体的功能实现。

继承一个抽象类的时候,子类必须定义父类中的所有抽象方法;另外,这些方法的访问控制必须和父类中一样(或者更为宽松,更加宽松也可以)。例如某个抽象方法被声明为受保护的,那么子类中实现的方法就应该声明为受保护的或者公有的,而不能定义为私有的。

子类方法可以包含父类抽象方法中不存在的可选参数。

<?php
abstract class AbstractClass
{
 // 强制要求子类定义这些方法
    abstract protected function getValue();
    abstract protected function prefixValue($prefix);

    // 普通方法(非抽象方法)
    public function printOut() {
        print $this->getValue() . PHP_EOL;
    }
}

class ConcreteClass1 extends AbstractClass
{
    protected function getValue() {
        return "ConcreteClass1";
    }

    public function prefixValue($prefix) {
        return "{$prefix}ConcreteClass1";
    }
}

class ConcreteClass2 extends AbstractClass
{
    public function getValue() {
        return "ConcreteClass2";
    }

    public function prefixValue($prefix) {
        return "{$prefix}ConcreteClass2";
    }
}

$class1 = new ConcreteClass1;
$class1->printOut();
echo $class1->prefixValue(‘FOO_‘) . PHP_EOL;

$class2 = new ConcreteClass2;
$class2->printOut();
echo $class2->prefixValue(‘FOO_‘) . PHP_EOL;
?>
//返回
ConcreteClass1
FOO_ConcreteClass1
ConcreteClass2
FOO_ConcreteClass2

Static 关键字

声明类属性或方法为 static(静态),就可以不实例化类而直接访问。

静态属性不能被实例访问,但是静态方法可以。

由于静态方法不需要通过对象即可调用,所以伪变量 $this 在静态方法中不可用。

静态属性不可以由对象通过 -> 操作符来访问。

<?php
class Foo {
  public static $my_static = ‘foo‘;

  public function staticValue() {
     return self::$my_static;
  }
}

print Foo::$my_static . PHP_EOL;    //返回foo不用实例化可以直接访问
$foo = new Foo();

print $foo->staticValue() . PHP_EOL;    //返回foo,因为实例化以后不可以访问static的属性
?> 

final关键字 


PHP 5 新增了一个 final 关键字。如果父类中的方法被声明为 final,则子类无法覆盖该方法。如果一个类被声明为 final,则不能被继承。

<?php
class BaseClass {
   public function test() {
       echo "BaseClass::test() called" . PHP_EOL;
   }

   final public function moreTesting() {    //final在public前
       echo "BaseClass::moreTesting() called"  . PHP_EOL;
   }
}

class ChildClass extends BaseClass {
   public function moreTesting() {    //子类无法覆盖该方法,继承还是可以的
       echo "ChildClass::moreTesting() called"  . PHP_EOL;
   }
}
// 报错信息 Fatal error: Cannot override final method BaseClass::moreTesting()
?>

调用父类构造方法:

class BaseClass {
   function __construct() {
       print "BaseClass 类中构造方法" . PHP_EOL;
   }
}
class SubClass extends BaseClass {
   function __construct() {
       parent::__construct();  // 子类构造方法不能自动调用父类的构造方法
       print "SubClass 类中构造方法" . PHP_EOL;
   }
}
class OtherSubClass extends BaseClass {
    // 继承 BaseClass 的构造方法
}

// 调用 BaseClass 构造方法
$obj = new BaseClass();
//返回/BaseClass 类中构造方法

// 调用 BaseClass、SubClass 构造方法
$obj = new SubClass();
//返回BaseClass 类中构造方法
//返回SubClass 类中构造方法

// 调用 BaseClass 构造方法
$obj = new OtherSubClass();
//返回BaseClass 类中构造方法

原文地址:https://www.cnblogs.com/0-lingdu/p/9623918.html

时间: 2024-11-25 21:36:16

php编程 之 php基础三的相关文章

Unix网络编程 之 socket基础

基本结构 (这部分的地址均为网络地址<网络字节序>) 1.struct sockaddr:通用套接字地址结构 此结构用于存储通用套接字地址. 数据结构定义: typedef unsigned short sa_family_t; struct sockaddr { sa_family_t sa_family; /* address family, AF_xxx */ char sa_data[14]; /* 14 bytes of protocol address */ };    sa_fa

java编程思想总结(三)

java编程思想总结(三) java编程思想总结是一个持续更新的系列,是本人对自己多年工作中使用到java的一个经验性总结,也是温故而知新吧,因为很多基础的东西过了这么多年,平时工作中用不到也会遗忘掉,所以看看书,上上网,查查资料,也算是记录下自己的笔记吧,过一段时间之后再来看看也是蛮不错的,也希望能帮助到正在学习的人们,本系列将要总结一下几点: 面向对象的编程思想 java的基本语法 一些有趣的框架解析 实战项目的整体思路 代码的优化以及性能调优的几种方案 整体项目的规划和视角 其它遗漏的东西

C++ Primer学习笔记32_面向对象编程(3)--继承(三):多重继承、虚继承与虚基类

C++ Primer学习笔记32_面向对象编程(3)--继承(三):多重继承.虚继承与虚基类 一.多重继承 在C++语言中,一个派生类可以从一个基类派生,称为单继承:也可以从多个基类派生,称为多继承. 多重继承--一个派生类可以有多个基类 class <派生类名> : <继承方式1> <基类名1>,<继承方式2> <基类名2>,... { <派生类新定义成员> }; 可见,多继承与单继承的区别从定义格式上看,主要是多继承的基类多于一个

shell 入门基础三

    linux shell 编程 1什么是bash shell 变量 shell变量可分为两类: 局部变量和环境变量. 局部变量只在创建它们的shell中可用.而环境变量则可以在创建它们的shell及其派生出来的任意子进程中使用.有些变量是用户创建的,其他的则是专用shell变量.变量名必须以字母或下划线字符开头.其余的字符可以是字母.数字(0~9)或下划线字符.任何其他的字符都标志着变量名的终止.名字是大小写敏感的.给变量赋值时,等号周围不能有任何空白符.为了给变量赋空值,可以在等号后跟一

Linux高性能服务器编程——Linux网络基础API及应用

 Linux网络编程基础API 详细介绍了socket地址意义极其API,在介绍数据读写API部分引入一个有关带外数据发送和接收的程序,最后还介绍了其他一些辅助API. socket地址API 主机字节序和网络字节序 字节序分为大端字节序和小端字节序.小端字节序又被称为主机字节序,大端字节序被称为网络字节序.大端字节序是指一个整数的高位字节存储在内存的低地址处,低位字节存储在内存的高地址处.小端字节序则相反. Linux提供如下四个函数完成主机字节序与网络字节序之间的转换: #include

零基础学编程:零基础学HTML+CSS (第3版) 完整pdf扫描版

零基础学编程:零基础学HTML+CSS(第3版)站在零基础学习的角度,以通俗易懂的语言,结合丰富多彩的实例,来帮助初学者学习和掌握HTML语言和CSS样式设计.本书列举了大量的小型实例.综合实例,并包含3个项目案例,内容详尽.实例丰富.叙述清晰.本书主要分为四篇:第一篇为第1-9章,讲解了网页文字.字体.表格.段落.超级链接.图像.表单.框架.多媒体等技术:第二篇为第10-11章,对DIV+CSS的语法和相关属性进行了详细的解释和说明:第三篇为第12~20章,详细介绍了CSS的字体.文本.背景.

零基础学大数据编程需要哪些基础?

零基础学大数据编程需要哪些基础?程序员薪酬高.工作环境好,是很多同学向往的职业,让很多非计算机专业的同学羡慕不已.非计算机专业难道就不能成为程序员了吗? 一.零基础学大数据编程需要基础: 1.数学基础 从计算机发展和应用的历史来看计算机的数学模型和体系结构等都是有数学家提出的,最早的计算机也是为数值计算而设计的.因此,要学好计算机就要有一定的数学基础,出学者有高中水平就差不多了. 2.逻辑思维能力的培养 学程序设计要有一定的逻辑思维能力,逻思力的培养要长时间的实践锻炼. 要想成为一名优秀的程序员

BeagleBone Black板第六课:C++编程控制GPIO基础

BBB板第六课:C++编程控制GPIO基础 在一上课我们通过Shell脚本编程实现了对GPIO端口的简单输出控制,实现对两个LED指示灯的交替点亮和关闭,接下来的一两节课,将通过C++程序来实现Shell脚本的功能.为了实现对应的程序控制,我查阅了好多资料,测试过程中发觉网上的一些程序套用过来总是出现各种各样的编译错误,压根就控制不了BBB板,不知是我的BBB板太新,还是以前的程序太旧.最后还是从头开始,重新研究BBB板的文件系统,找出头文件,找出所有相关的函数,终于实现GPIO的C++程序控制

Python全栈开发【基础三】

Python全栈开发[基础三]  本节内容: 函数(全局与局部变量) 递归 函数 一.定义和使用 函数最重要的是减少代码的重用性和增强代码可读性 1 def 函数名(参数): 2 3 ... 4 函数体 5 ... 6 返回值 函数的定义主要有如下要点: def:表示函数的关键字 函数名:函数的名称,日后根据函数名调用函数 函数体:函数中进行一系列的逻辑计算 参数:为函数体提供数据 返回值:当函数执行完毕后,可以给调用者返回数据. 总结使用函数的好处: 1.减少代码重用 2.保持一致性,易维护