ホームページ >PHPフレームワーク >Laravel >Laravelで一般的に使用されるPHP構文をまとめます。

Laravelで一般的に使用されるPHP構文をまとめます。

藏色散人
藏色散人転載
2021-09-09 11:28:262195ブラウズ

序文

Laravel フレームワークコンポーネント化された設計と設計の適切な使用のためパターンにより、フレームワーク自体が簡潔になり、拡張が容易になります。 ThinkPHP の統合関数フレームワーク (すべての関数を使用する、または関数を使用しない) とは異なり、Laravel ではコンポーザー ツールを使用してパッケージを管理し、関数を追加したい場合はコンポーネントを直接追加できます。たとえば、クローラーを作成し、ページ コレクション コンポーネントを使用する場合: composer require jaeger/querylist

この記事では、Laravel で頻繁に使用される PHP の機能と新しい構文を簡単に紹介します。詳細についてはそれを参照してください。

コンポーネントベースの開発

Laravel は、PSR-4 仕様に準拠したコンポーザー ツールのおかげでコンポーネントベースの開発を実行します。このツールは、名前空間と自動読み込みを使用してプロジェクト ファイルを整理します。詳細: Composer の自動読み込みメカニズム

名前空間

名前の競合

チーム内で共同作業し、サードパーティに依存するコードを導入する場合、クラス、関数、インターフェイスが重複して表示されることがよくあります。名前。例:

<?php     
# google.php
class User 
{
    private $name;
}
<?php     
# mine.php
// 引入第三方依赖
include &#39;google.php&#39;;

class User
{
    private $name;
}

$user = new User();    // 命名冲突

クラス User が同時に定義されているため、名前の競合が発生します:

Laravelで一般的に使用されるPHP構文をまとめます。

##解決策

PHP 5.3 より 入門の開始 PHP マニュアルを参照して、名前空間には

名前の競合を回避する 名前を短くする という 2 つの機能があることを確認してください。たとえば、名前空間を使用した後:

<?php # google.php
namespace Google;

// 模拟第三方依赖
class User {
    private $name = &#39;google&#39;;

    public function getName() {
        echo $this->name . PHP_EOL;
    }
}
<?php # mine.php
namespace Mine;

// 导入并命名别名
use Google as G;

// 导入文件使得 google.php 命名空间变为 mine.php 的子命名空间
include &#39;google.php&#39;;

/* 避免了命名冲突 */
class User
{
    private $name = &#39;mine&#39;;

    public function getName() {
        echo $this->name . PHP_EOL;
    }
}

/* 保持了命名简短 */
// 如果没有命名空间,为了类名也不冲突,可能会出现这种函数名
// $user = new Google_User();
// Zend 风格并不提倡
$user = new G\User();

// 为了函数名也不冲突,可能会出现这种函数名
// $user->google_get_name()
$user->getName();

$user = new User();
$user->getName();
実行:

$ php demo.php
google
mine
PSR仕様

実際、名前空間はファイル名とは何の関係もありませんが、 PSR 標準要件: 名前空間はファイル パスと一致し、ファイル名はクラス名と一致します。たとえば、

laravel-demo/app/Http/Controllers/Auth/LoginController.php はデフォルトで Laravel によって生成され、その名前空間は App\Http\Controllers\Auth & クラス名 LoginController

仕様に従い、上記の

mine.phpgoogle.php は両方とも User.php という名前にする必要があります。

名前空間演算子と

__NAMESPACE__ マジック定数
...
// $user = new User();
$user = new namespace\User();    // 值为当前命名空间
$user->getName();

echo __NAMESPACE__ . PHP_EOL;    // 直接获取当前命名空间字符串    // 输出 Mine

3 つの名前空間のインポート

<?php namespace CurrentNameSpace;

// 不包含前缀
$user = new User();        # CurrentNameSpace\User();

// 指定前缀
$user = new Google\User();    # CurrentNameSpace\Google\User();

// 根前缀
$user = new \Google\User();    # \Google\User();

グローバル名前空間

参照クラスの場合、Ifこの関数では名前空間が指定されていないため、デフォルトでは

__NAMESPACE__ で検索されます。グローバル クラスを参照するには:

<?php namespace Demo;

// 均不会被使用到
function strlen() {}
const INI_ALL = 3;
class Exception {}

$a = \strlen(&#39;hi&#39;);         // 调用全局函数 strlen
$b = \CREDITS_GROUP;          // 访问全局常量 CREDITS_GROUP
$c = new \Exception(&#39;error&#39;);   // 实例化全局类 Exception
複数のインポートと複数の名前空間

// use 可一次导入多个命名空间
use Google,
    Microsoft;

// 良好实践:每行一个 use
use Google;
use Microsoft;
<?php // 一个文件可定义多个命名空间
namespace Google {
    class User {}
}    
    
namespace Microsoft {
    class User {}
}   

// 良好实践:“一个文件一个类”

定数と関数のインポート

PHP 5.6 以降では、

use functionuse const 関数と定数をそれぞれインポートします。使用:

# google.php
const CEO = 'Sundar Pichai';
function getMarketValue() {
    echo '770 billion dollars' . PHP_EOL;
}
# mine.php
use function Google\getMarketValue as thirdMarketValue;
use const Google\CEO as third_CEO;

thirdMarketValue();
echo third_CEO;
実行:

$ php mine.php
google
770 billion dollars
Sundar Pichaimine
Mine
ファイルに含まれる

手動読み込み

指定したファイルを導入するには、

include または require を使用します (リテラル解釈) require エラーはコンパイル エラーを報告し、スクリプトを中断しますが、include エラーはコンパイル エラーを報告するだけであることに注意してください。警告が表示され、スクリプトは引き続き実行されます。

include ファイルを指定すると、まず php.ini の構成項目

include_path で指定されたディレクトリが検索されます。見つからない場合は、現在のディレクトリが検索されます:

Laravelで一般的に使用されるPHP構文をまとめます。

<?php     
// 引入的是 /usr/share/php/System.php
include &#39;System.php&#39;;
自動ロード

void __autoload(string $class) はクラスを自動的にロードできますが、通常は spl_autoload_register を使用して手動で登録します。 <pre class="brush:php;toolbar:false">&lt;?php // 自动加载子目录 classes 下 *.class.php 的类定义 function __autoload($class) { include &amp;#39;classes/&amp;#39; . $class . &amp;#39;.class.php&amp;#39;; } // PHP 5.3 后直接使用匿名函数注册 $throw = true; // 注册出错时是否抛出异常 $prepend = false; // 是否将当前注册函数添加到队列头 spl_autoload_register(function ($class) { include &amp;#39;classes/&amp;#39; . $class . &amp;#39;.class.php&amp;#39;; }, $throw, $prepend);</pre></pre>composer によって生成された自動ロード ファイル

laravel-demo/vendor/composer/autoload_real.php

で次のことがわかります: <pre class="brush:php;toolbar:false">class ComposerAutoloaderInit8b41a {     private static $loader;     public static function loadClassLoader($class)     {         if ('Composer\Autoload\ClassLoader' === $class) {             // 加载当前目录下文件             require __DIR__ . '/ClassLoader.php';         }     }           public static function getLoader()     {         if (null !== self::$loader) {             return self::$loader;         }              // 注册自己的加载器         spl_autoload_register(array('ComposerAutoloaderInit8b41a6', 'loadClassLoader'), true, true);         self::$loader = $loader = new \Composer\Autoload\ClassLoader();         spl_autoload_unregister(array('ComposerAutoloaderInit8b41a6a', 'loadClassLoader'));         ...      }       ... }</pre>ここでは、特に Laravel がどのように自動的に実行するかについてのみ説明します。全体として読み込み中 はい、次の記事で詳しく説明します。

Reflection

PHP マニュアルを参照してください。これは、実行時にオブジェクトの完全な情報を取得すると単純に理解できます。リフレクションには 5 つのクラスがあります:

ReflectionClass     // 解析类名
ReflectionProperty     // 获取和设置类属性的信息(属性名和值、注释、访问权限)
ReflectionMethod     // 获取和设置类函数的信息(函数名、注释、访问权限)、执行函数等
ReflectionParameter    // 获取函数的参数信息
ReflectionFunction    // 获取函数信息

たとえば、

ReflectionClass

の使用: <pre class="brush:php;toolbar:false">&lt;?php class User { public $name; public $age; public function __construct($name = &amp;#39;Laruence&amp;#39;, $age = 35) { $this-&gt;name = $name;         $this-&gt;age  = $age;     }     public function intro() {         echo '[name]: ' . $this-&gt;name . PHP_EOL;         echo '[age]: '  . $this-&gt;age  . PHP_EOL;     } } reflect('User'); // ReflectionClass 反射类使用示例 function reflect($class) {     try {         $ref = new ReflectionClass($class);         // 检查是否可实例化         // interface、abstract class、 __construct() 为 private 的类均不可实例化         if (!$ref-&gt;isInstantiable()) {             echo &quot;[can't instantiable]: ${class}\n&quot;;         }         // 输出属性列表         // 还能获取方法列表、静态常量等信息,具体参考手册         foreach ($ref-&gt;getProperties() as $attr) {             echo $attr-&gt;getName() . PHP_EOL;         }         // 直接调用类中的方法,个人认为这是反射最好用的地方         $obj = $ref-&gt;newInstanceArgs();         $obj-&gt;intro();     } catch (ReflectionException $e) {             // try catch 机制真的不优雅             // 相比之下 Golang 的错误处理虽然繁琐,但很简洁         echo '[reflection exception: ]' . $e-&gt;getMessage();     } }</pre>Run:

$ php reflect.php
name
age
[name]: Laruence
[age]: 35

他の 4 つのリフレクション クラスの場合マニュアルのデモを参照してください。

後期静的バインディング

最初に PHP マニュアルを参照して例を見てください:

<?php class Base
{
        // 后期绑定不局限于 static 方法
    public static function call() {
        echo &#39;[called]: &#39; . __CLASS__ . PHP_EOL;
    }

    public static function test() {
        self::call();        // self   取值为 Base  直接调用本类中的函数
        static::call();        // static 取值为 Child 调用者
    }
}

class Child extends Base
{
    public static function call() {
        echo &#39;[called]: &#39; . __CLASS__ . PHP_EOL;
    }
}


Child::test();

出力:

$ php late_static_bind.php
[called]: Base
[called]: Child

オブジェクトがインスタンス化されるとき、

self::

はそれが定義されているクラスをインスタンス化し、static:: はそれを呼び出すクラスをインスタンス化します。 trait

基本的な使い方

PHPマニュアル参照 PHPは単一継承ですが、5.4以降では「クラス」を水平結合することで実現できるようになりました。多重継承とは、実際には、繰り返される関数をトライアットに分割して異なるファイルに配置し、必要に応じて use キーワードを使用して導入および結合することです。継承は、Golang の構造体詰め込みの組み合わせと同様に実装できます。例:

<?php class DemoLogger
{
    public function log($message, $level) {
        echo "[message]: $message", PHP_EOL;
        echo "[level]: $level", PHP_EOL;
    }
}

trait Loggable
{
    protected $logger;

    public function setLogger($logger) {
        $this->logger = $logger;
    }

    public function log($message, $level) {
        $this->logger->log($message, $level);
    }
}

class Foo
{
        // 直接引入 Loggable 的代码片段
    use Loggable;
}

$foo = new Foo;
$foo->setLogger(new DemoLogger);
$foo->log('trait works', 1);

実行:

$ php trait.php
[message]: trait works
[level]: 1

その他の参照: PHP Trait について理解していること

重要なプロパティ

Priority

現在のクラスの関数はトレイトの同じ名前の関数を上書きし、トレイトは親クラスの同じ名前の関数を上書きします (

use trait

は、現在のクラスがトレイトを直接上書きするのと同等です) trait function Conflict

複数のトレイトの同時導入は

,

で区切ることができます、つまり多重継承。 <p>多个 trait 有同名函数时,引入将发生命名冲突,使用 <code>insteadof 来指明使用哪个 trait 的函数。

重命名与访问控制

使用 as 关键字可以重命名的 trait 中引入的函数,还可以修改其访问权限。

其他

trait 类似于类,可以定义属性、方法、抽象方法、静态方法和静态属性。

下边的苹果、微软和 Linux 的小栗子来说明:

<?php trait Apple
{
    public function getCEO() {
        echo &#39;[Apple CEO]: Tim Cook&#39;, PHP_EOL;
    }

    public function getMarketValue() {
        echo &#39;[Apple Market Value]: 953 billion&#39;, PHP_EOL;
    }
}


trait MicroSoft
{
    public function getCEO() {
        echo &#39;[MicroSoft CEO]: Satya Nadella&#39;, PHP_EOL;
    }

    public function getMarketValue() {
        echo &#39;[MicroSoft Market Value]: 780 billion&#39;, PHP_EOL;
    }

    abstract public function MadeGreatOS();

    static public function staticFunc() {
        echo &#39;[MicroSoft Static Function]&#39;, PHP_EOL;
    }

    public function staticValue() {
        static $v;
        $v++;
        echo &#39;[MicroSoft Static Value]: &#39; . $v, PHP_EOL;
    }
}


// Apple 最终登顶,成为第一家市值超万亿美元的企业
trait Top
{
    // 处理引入的 trait 之间的冲突
    use Apple, MicroSoft {
        Apple::getCEO insteadof MicroSoft;
        Apple::getMarketValue insteadof MicroSoft;
    }
}


class Linux
{
    use Top {
            // as 关键字可以重命名函数、修改权限控制
        getCEO as private noCEO;
    }

    // 引入后必须实现抽象方法
    public function MadeGreatOS() {
        echo &#39;[Linux Already Made]&#39;, PHP_EOL;
    }

    public function getMarketValue() {
        echo &#39;[Linux Market Value]: Infinity&#39;, PHP_EOL;
    }
}

$linux = new Linux();
// 和 extends 继承一样
// 当前类中的同名函数也会覆盖 trait 中的函数
$linux->getMarketValue();

// trait 中可以定义静态方法
$linux::staticFunc();

// 在 trait Top 中已解决过冲突,输出库克
$linux->getCEO();
// $linux->noCEO();        // Uncaught Error: Call to private method Linux::noCEO() 

// trait 中可以定义静态变量
$linux->staticValue();
$linux->staticValue();

运行:

$ php trait.php
[Linux Market Value]: Infinity
[MicroSoft Static Function]
[Apple CEO]: Tim Cook
[MicroSoft Static Value]: 1
[MicroSoft Static Value]: 2

总结

本节简要提及了命名空间、文件自动加载、反射机制与 trait 等,Laravel 正是恰如其分的利用了这些新特性,才实现了组件化开发、服务加载等优雅的特性。

以上がLaravelで一般的に使用されるPHP構文をまとめます。の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事はwuYin/blogで複製されています。侵害がある場合は、admin@php.cn までご連絡ください。