PSR-12 編碼規(guī)范擴(kuò)充

image

文章轉(zhuǎn)發(fā)自專業(yè)的Laravel開(kāi)發(fā)者社區(qū)卓起,原始鏈接:https://learnku.com/laravel/t/35080

編碼風(fēng)格擴(kuò)充指南

文章中的關(guān)鍵詞 MUST 磷蜀, MUST NOT 亮靴, REQUIREDSHALLSHALL NOT 坪仇, SHOULD
SHOULD NOT 垃你, RECOMMENDED 椅文, MAY ,和 OPTIONAL 都在 RFC 2119 中進(jìn)行來(lái)解釋惜颇。

摘要

此規(guī)范起到繼承皆刺,擴(kuò)展和替換 [PSR-2][] 的作用, 同時(shí)編碼風(fēng)格遵守 [PSR-1][] 這個(gè)基礎(chǔ)編碼標(biāo)準(zhǔn)凌摄。
和 [PSR-2][] 一樣羡蛾, 此規(guī)范的目的是減少不同人在閱讀代碼時(shí)認(rèn)知沖突。 它通過(guò)列舉一套如何格式化 PHP 代碼的公共的規(guī)則和期望來(lái)實(shí)現(xiàn)這個(gè)目標(biāo)锨亏。 PSR 力圖提供一套方法痴怨,編碼風(fēng)格工具可以利用忙干,項(xiàng)目可以遵守,開(kāi)發(fā)人員可以方便的在不同的項(xiàng)目中使用浪藻。當(dāng)各個(gè)的開(kāi)發(fā)人員在進(jìn)行多項(xiàng)目合作的時(shí)候捐迫,它可以幫助在這些項(xiàng)目中提供一套通用的指導(dǎo)。所以爱葵,本指南的價(jià)值不是規(guī)則本身施戴,而是這些規(guī)則的共享。

[PSR-2][] 在 2012 年被接受萌丈,隨后 PHP 經(jīng)歷了很多變化赞哗,影響了編碼風(fēng)格。同時(shí) [PSR-2] 是 PHP 編碼時(shí)候的基礎(chǔ)功能辆雾,被廣泛的采用肪笋。因此,PSR 力圖通過(guò)一種更加現(xiàn)代的方式說(shuō)明 PSR-2 的內(nèi)容和新功能度迂,并對(duì) PSR-2 進(jìn)行更正涂乌。

以前的語(yǔ)言版本

在整個(gè)文檔中,任何說(shuō)明都可以被忽略英岭,如果它們不存在于你項(xiàng)目所支持的 PHP 版本中湾盒。

例如

此示例包含以下一些規(guī)則作為快速概述:

<?php

declare(strict_types=1);

namespace Vendor\Package;

use Vendor\Package\{ClassA as A, ClassB, ClassC as C};
use Vendor\Package\SomeNamespace\ClassD as D;

use function Vendor\Package\{functionA, functionB, functionC};

use const Vendor\Package\{ConstantA, ConstantB, ConstantC};

class Foo extends Bar implements FooInterface
{
    public function sampleFunction(int $a, int $b = null): array
    {
        if ($a === $b) {
            bar();
        } elseif ($a > $b) {
            $foo->bar($arg1);
        } else {
            BazClass::bar($arg2, $arg3);
        }
    }

    final public static function bar()
    {
        // 方法內(nèi)容
    }
}

2. 總則

2.1 基本編碼標(biāo)準(zhǔn)

代碼必須遵循[PSR-1]中列出的所有規(guī)則。

PSR-1中的術(shù)語(yǔ) 'StudlyCaps' 必須解釋為 PascalCase (帕斯卡命名法:大駝峰式命名法)诅妹,其中每個(gè)單詞的第一個(gè)字母大寫罚勾,包括第一個(gè)字母。

2.2 文件

所有 PHP 文件只能使用Unix LF (換行符) 結(jié)尾吭狡。

所有的 PHP 文件都必須以非空行結(jié)尾尖殃,以一個(gè) LF 結(jié)尾。

在僅包含 PHP 代碼的文件中划煮,必須省略結(jié)尾的 送丰?> 標(biāo)記。

2.3 代碼行

行長(zhǎng)度不得有硬限制器躏。

行長(zhǎng)度的軟限制必須為120個(gè)字符。

行的長(zhǎng)度不應(yīng)超過(guò)80個(gè)字符揽浙;超過(guò)該長(zhǎng)度的行應(yīng)拆分為多個(gè)后續(xù)行馅巷,每個(gè)行的長(zhǎng)度不應(yīng)超過(guò)80個(gè)字符走敌。

行尾不能有尾隨空格。

可以添加空行以提高可讀性并指示相關(guān)的代碼塊,除非明確禁止纲刀。

每行不能有多個(gè)語(yǔ)句示绊。

2.4 縮進(jìn)

代碼必須為每個(gè)縮進(jìn)級(jí)別使用4個(gè)空格的縮進(jìn)面褐,并且不能使用縮進(jìn)標(biāo)簽展哭。

2.5 關(guān)鍵詞和類型

PHP 的所有關(guān)鍵字和類型 [1][2]必須使用小寫匪傍。

PHP未來(lái)版本中新加的所有關(guān)鍵字和類型也都必須使用小寫役衡。

類型關(guān)鍵字必須使用縮寫。使用 bool 而不是 boolean柑船,使用 int 而不是 integer 等等。

3. 聲明及塘、命名空間以及導(dǎo)入

一個(gè)PHP文件的頭部可能會(huì)包含多個(gè)塊笙僚。如果包含多個(gè)塊肋层,則每個(gè)塊都必須用空白行和其他塊分隔,并且塊內(nèi)不能包含空白行栋猖。所有的塊都必須按照下面的順序排列汪榔,如果不存在該塊則忽略蒲拉。

  • PHP文件開(kāi)始標(biāo)簽: <?php痴腌。
  • 文件級(jí)文檔塊雌团。
  • 一個(gè)或多個(gè)聲明語(yǔ)句。
  • 命名空間聲明語(yǔ)句士聪。
  • 一個(gè)或多個(gè)基于類的 use 聲明語(yǔ)句。
  • 一個(gè)或多個(gè)基于方法的 use 聲明語(yǔ)句雨涛。
  • 一個(gè)或多個(gè)基于常量的 use 聲明語(yǔ)句。
  • 其余代碼。

當(dāng)文件包含HTML和PHP的混合代碼時(shí)胀糜,可以使用上面列出的任何部分距帅。如果是這種情況的話,即時(shí)代碼的其他部分包含有PHP結(jié)束符括堤,然后再包含HTML和PHP代碼碌秸,聲明绍移、命名空間和導(dǎo)入語(yǔ)句塊也必須放在文件的頂部。

什么時(shí)候開(kāi)始 <讥电?php 標(biāo)簽位于文件的第一行蹂窖,它必須位于自己的行,沒(méi)有其他語(yǔ)句恩敌,除非它是一個(gè)包含 PHP 之外的標(biāo)記的文件打開(kāi)和關(guān)閉標(biāo)記瞬测。

import語(yǔ)句不能以前導(dǎo)反斜杠開(kāi)頭,因?yàn)樗鼈儽仨毷冀K完全合格纠炮。

以下示例演示了所有塊的完整列表:

<?php

/**
 * This file contains an example of coding styles.
 */

declare(strict_types=1);

namespace Vendor\Package;

use Vendor\Package\{ClassA as A, ClassB, ClassC as C};
use Vendor\Package\SomeNamespace\ClassD as D;
use Vendor\Package\AnotherNamespace\ClassE as E;

use function Vendor\Package\{functionA, functionB, functionC};
use function Another\Vendor\functionD;

use const Vendor\Package\{CONSTANT_A, CONSTANT_B, CONSTANT_C};
use const Another\Vendor\CONSTANT_D;

/**
 * FooBar is an example class.
 */
class FooBar
{
    // ... 其他php代碼 ...
}

深度不能超過(guò)兩層的復(fù)合名稱空間月趟,因此以下展示了允許的最大復(fù)合深度。

<?php

use Vendor\Package\SomeNamespace\{
    SubnamespaceOne\ClassA,
    SubnamespaceOne\ClassB,
    SubnamespaceTwo\ClassY,
    ClassZ,
};

并且不允許以下內(nèi)容:

<?php

use Vendor\Package\SomeNamespace\{
    SubnamespaceOne\AnotherNamespace\ClassA,
    SubnamespaceOne\ClassB,
    ClassZ,
};

當(dāng)希望在 PHP 外部包含標(biāo)記的文件中聲明嚴(yán)格類型時(shí)打開(kāi)和關(guān)閉標(biāo)簽恢口,聲明必須寫在文件的第一行并且包含在一個(gè)開(kāi)始的 PHP 標(biāo)簽孝宗,以及嚴(yán)格的類型聲明和結(jié)束標(biāo)簽。

例如:

<?php declare(strict_types=1) ?>
<html>
<body>
    <?php
        // ... 其他 PHP 代碼  ...
    ?>
</body>
</html>

聲明語(yǔ)句不能包含空格弧蝇,并且必須完全是 declare(strict_types=1) (帶有可選的分號(hào)終止符)。

允許使用塊聲明語(yǔ)句折砸,并且必須按照以下的格式設(shè)置看疗。注意的位置括號(hào)和間距:

declare(ticks=1) {
    // 一些代碼
}

4. 類,屬性睦授,和方法

這里的『類』指的是所有類两芳,接口,以及 trait 去枷。

任何注釋和語(yǔ)句 不得 跟在其右花括號(hào)后的同一行怖辆。

當(dāng)實(shí)例化一個(gè)類時(shí),后面的圓括號(hào) 必須 寫出來(lái)删顶,即使沒(méi)有參數(shù)傳進(jìn)其構(gòu)造函數(shù)竖螃。

new Foo();

4.1 繼承和實(shí)現(xiàn)

關(guān)鍵字 繼承實(shí)現(xiàn) 必須 在類名的同一行聲明。

類的左花括號(hào) 必須 另起一行逗余;右花括號(hào) 必須 跟在類主體的下一行特咆。

類的左花括號(hào) 必須 獨(dú)自成行,且 不得 在其上一行或下一行存在空行录粱。

右花括號(hào) 必須 獨(dú)自成行腻格,且 不得 在其上一行存在空行。

<?php

namespace Vendor\Package;

use FooClass;
use BarClass as Bar;
use OtherVendor\OtherPackage\BazClass;

class ClassName extends ParentClass implements \ArrayAccess, \Countable
{
    // 常量啥繁,屬性菜职,方法
}

如果有接口, 實(shí)現(xiàn) 接口和 繼承父類 可以 分為多行旗闽,前者每行需縮進(jìn)一次酬核。當(dāng)這么做時(shí)蜜另,第一個(gè)接口 必須 寫在下一行,且每行 必須 只能寫一個(gè)接口愁茁。

<?php

namespace Vendor\Package;

use FooClass;
use BarClass as Bar;
use OtherVendor\OtherPackage\BazClass;

class ClassName extends ParentClass implements
    \ArrayAccess,
    \Countable,
    \Serializable
{
    // 常量蚕钦,屬性,方法
}

4.2 使用 trait

在類里面用于實(shí)現(xiàn) trait 的關(guān)鍵字 use 必須 在左花括號(hào)的下一行聲明鹅很。

<?php

namespace Vendor\Package;

use Vendor\Package\FirstTrait;

class ClassName
{
    use FirstTrait;
}

每個(gè)導(dǎo)入類的 trait 必須 每行一個(gè)包含聲明嘶居,且每個(gè)包含聲明 必須 有其 use 導(dǎo)入語(yǔ)句。

<?php

namespace Vendor\Package;

use Vendor\Package\FirstTrait;
use Vendor\Package\SecondTrait;
use Vendor\Package\ThirdTrait;

class ClassName
{
    use FirstTrait;
    use SecondTrait;
    use ThirdTrait;
}

在類文件中促煮,如果在使用'use Trait'之后沒(méi)有其他內(nèi)容了 邮屁,類名右大括號(hào)必須另起一行。

<?php

namespace Vendor\Package;

use Vendor\Package\FirstTrait;

class ClassName
{
    use FirstTrait;
}

如有其他內(nèi)容菠齿,兩者之間需空一行佑吝。

<?php

namespace Vendor\Package;

use Vendor\Package\FirstTrait;

class ClassName
{
    use FirstTrait;

    private $property;
}

當(dāng)使用' insteadof '和' as '運(yùn)算符時(shí),它們必須如圖所示使用绳匀,注意縮進(jìn)芋忿、間距和另起一行。

<?php

class Talker
{
    use A, B, C {
        B::smallTalk insteadof A;
        A::bigTalk insteadof C;
        C::mediumTalk as FooBar;
    }
}

4.3 屬性和常量

所有屬性 必須 聲明可見(jiàn)性疾棵。

如果你的項(xiàng)目 PHP 最小版本支持常量可見(jiàn)性( PHP 7.1 或以上)戈钢,所有常量 必須 聲明可見(jiàn)性。

關(guān)鍵字 var 不得 用于聲明屬性是尔。

每條聲明語(yǔ)句 不得 聲明多于一個(gè)屬性殉了。

屬性名 不得 用單個(gè)下劃線開(kāi)頭表明其受保護(hù)的或私有的可見(jiàn)性。也就是說(shuō)拟枚,一個(gè)下劃線開(kāi)頭顯然是沒(méi)有意義的薪铜。

類型聲明和屬性名之間 必須 有一個(gè)空格。

一個(gè)屬性聲明看上去如下所示:

<?php

namespace Vendor\Package;

class ClassName
{
    public $foo = null;
    public static int $bar = 0;
}

4.4 方法和函數(shù)

所有的方法 必須 事先聲明類型恩溅。

方法命名 一定不可 用單個(gè)下劃線來(lái)區(qū)分是 protectedprivate 類型隔箍。也就是說(shuō),不要用一個(gè)沒(méi)有意義的下劃線開(kāi)頭脚乡。

方法和函數(shù)名稱中鞍恢,方法命名后面 一定不可 使用空格。方法開(kāi)始的花括號(hào) 必須 寫在方法聲明后自成一行每窖, 結(jié)束花括號(hào)也 必須 寫在方法后面自成一行帮掉。開(kāi)始左括號(hào)后和結(jié)束右括號(hào)前,都 一定不可 有空格符窒典。

一個(gè)方法的聲明應(yīng)該如下所示蟆炊。注意括號(hào),逗號(hào)瀑志,空格和花括號(hào)的位置:

<?php

namespace Vendor\Package;

class ClassName
{
    public function fooBarBaz($arg1, &$arg2, $arg3 = [])
    {
        // 方法主體
    }
}

一個(gè)函數(shù)的聲明應(yīng)該如下所示涩搓。注意括號(hào)污秆,逗號(hào),空格和花括號(hào)的位置:

<?php

function fooBarBaz($arg1, &$arg2, $arg3 = [])
{
    // 函數(shù)主體
}

4.5 方法和函數(shù)參數(shù)

在參數(shù)列表中昧甘, 不得 在每個(gè)逗號(hào)前存在空格良拼,且 必須 在每個(gè)逗號(hào)后有一個(gè)空格。

方法和函數(shù)中帶有默認(rèn)值的參數(shù) 必須 放在參數(shù)列表的最后充边。

<?php

namespace Vendor\Package;

class ClassName
{
    public function foo(int $arg1, &$arg2, $arg3 = [])
    {
        // 方法主體
    }
}

參數(shù)列表 可以 分為多行庸推,每行參數(shù)縮進(jìn)一次。當(dāng)這么做時(shí)浇冰,第一個(gè)參數(shù) 必須 放在下一行贬媒,且每行 必須 只能有一個(gè)參數(shù)。

當(dāng)參數(shù)列表分成多行時(shí)肘习,右圓括號(hào)和左花括號(hào) 必須 放在同一行且單獨(dú)成行际乘,兩者之間存在一個(gè)空格。

<?php

namespace Vendor\Package;

class ClassName
{
    public function aVeryLongMethodName(
        ClassTypeHint $arg1,
        &$arg2,
        array $arg3 = []
    ) {
        // 方法主體
    }
}

當(dāng)你定義一個(gè)返回值類型聲明時(shí)漂佩,冒號(hào)后面的類型聲明 必須 用空格符隔開(kāi)脖含。冒號(hào)和聲明 必須 在同一行,且跟參數(shù)列表后的結(jié)束括號(hào)之間沒(méi)有空格投蝉。

<?php

declare(strict_types=1);

namespace Vendor\Package;

class ReturnTypeVariations
{
    public function functionName(int $arg1, $arg2): string
    {
        return 'foo';
    }

    public function anotherFunction(
        string $foo,
        string $bar,
        int $baz
    ): string {
        return 'foo';
    }
}

在可空類型聲明中养葵,問(wèn)號(hào)和類型聲明之間不能有空格。

<?php

declare(strict_types=1);

namespace Vendor\Package;

class ReturnTypeVariations
{
    public function functionName(?string $arg1, ?int &$arg2): ?string
    {
        return 'foo';
    }
}

當(dāng)在參數(shù)之前使用引用運(yùn)算符 & 時(shí)墓拜,引用運(yùn)算符之后不能有空格港柜,例如上面的示例请契。

可變參數(shù)聲明的三個(gè)點(diǎn)和參數(shù)名稱之間不能有空格:

public function process(string $algorithm, ...$parts)
{
    // 函數(shù)體
}

當(dāng)同時(shí)使用引用運(yùn)算符和可變參數(shù)運(yùn)算符時(shí)咳榜,它們之間不能有任何空格:

public function process(string $algorithm, &...$parts)
{
    // 函數(shù)體
}

4.6 abstract, final, and static

如果是 abstract and final ,那么申明的時(shí)候必須是可見(jiàn)性聲明爽锥。

如果是 static 涌韩,聲明必須位于可見(jiàn)性聲明之后。

<?php

namespace Vendor\Package;

abstract class ClassName
{
    protected static $foo;

    abstract protected function zim();

    final public static function bar()
    {
        // 請(qǐng)求體
    }
}

4.7 方法和函數(shù)的調(diào)用

當(dāng)我們?cè)谶M(jìn)行方法或者函數(shù)調(diào)用的時(shí)候氯夷,方法或函數(shù)與左括號(hào)之間不能出現(xiàn)空格臣樱,在右括號(hào)之后也不能出現(xiàn)空格,并且在右括號(hào)之前也一定不能有空格腮考。在參數(shù)列表中雇毫,每個(gè)逗號(hào)前面一定不能有空格,每個(gè)逗號(hào)后面也一定不能有空格踩蔚。

<?php

bar();
$foo->bar($arg1);
Foo::bar($arg2, $arg3);

參數(shù)列表可以分為多行棚放,每行后面縮進(jìn)一次。這個(gè)做之后馅闽,列表中的第一行必須位于下一行飘蚯,并且每一行必須只有一個(gè)參數(shù)馍迄。跨多個(gè)行拆分單個(gè)參數(shù)(就像匿名函數(shù)或者數(shù)組那樣)并不構(gòu)成拆分參數(shù)列表本身局骤。

<?php

$foo->bar(
    $longArgument,
    $longerArgument,
    $muchLongerArgument
);
<?php

somefunction($foo, $bar, [
  // ...
], $baz);

$app->get('/hello/{name}', function ($name) use ($app) {
    return 'Hello ' . $app->escape($name);
});

5. 流程控制

如下是主要的流程控制風(fēng)格規(guī)則:

  • 流程控制關(guān)鍵詞之后 必須 要有一個(gè)空格
  • 左括號(hào)后面 不能 有空格
  • 右括號(hào)前面 不能 有空格
  • 右括號(hào)與左大括號(hào)之間 必須 要有一個(gè)空格
  • 流程主體 必須 要縮進(jìn)一次
  • 流程主體 必須 在左大括號(hào)之后另起一行
  • 右大括號(hào) 必須 在流程主體之后另起一行

每個(gè)流程控制主體 必須 以封閉的括號(hào)結(jié)束攀圈。這將標(biāo)準(zhǔn)化流程結(jié)構(gòu),同時(shí)減少由于流程中添加新的內(nèi)容而引入錯(cuò)誤的可能性峦甩。

5.1 if, elseif, else

if 結(jié)構(gòu)如下赘来。注意括號(hào),空格穴店,和大括號(hào)的位置撕捍;elseelseif 都在同一行,和右大括號(hào)一樣在主體的前面泣洞。

<?php

if ($expr1) {
    // if body
} elseif ($expr2) {
    // elseif body
} else {
    // else body;
}

關(guān)鍵詞 elseif 應(yīng)該 替換 else if忧风,這樣控制關(guān)鍵詞看起來(lái)像一個(gè)詞。

括號(hào)中的表達(dá)式 可能 會(huì)被分開(kāi)為多行球凰,每一行至少縮進(jìn)一次狮腿。如果這樣做,第一個(gè)條件 必須 在新的一行呕诉。右括號(hào)和左大括號(hào) 必須 在同一行缘厢,而且中間有一個(gè)空格。條件中間的布爾控制符 必須 在每一行的開(kāi)頭或者結(jié)尾甩挫,而不是混在一起贴硫。

<?php

if (
    $expr1
    && $expr2
) {
    // if body
} elseif (
    $expr3
    && $expr4
) {
    // elseif body
}

5.2 switch, case

switch 結(jié)構(gòu)如下。注意括號(hào)伊者,空格和大括號(hào)的位置英遭。case 必須 縮進(jìn)一次從switch開(kāi)始, break 關(guān)鍵詞 (或者其他終止關(guān)鍵詞) 必須 縮進(jìn)和 care 主體保持一致亦渗。必須 要有一個(gè)像 // 不終止 這樣的注釋在不為空且繼續(xù)的 care 主體之中挖诸。

<?php

switch ($expr) {
    case 0:
        echo 'First case, with a break';
        break;
    case 1:
        echo 'Second case, which falls through';
        // no break
    case 2:
    case 3:
    case 4:
        echo 'Third case, return instead of break';
        return;
    default:
        echo 'Default case';
        break;
}

括號(hào)中的表達(dá)式 可能 會(huì)被分開(kāi)多行,每一行至少要縮進(jìn)一次法精。如果這樣做多律,第一個(gè)條件 必須 在新的一行。右括號(hào)和左大括號(hào) 必須 在同一行搂蜓,而且中間有一個(gè)空格狼荞。條件中間的布爾控制符 必須 在沒(méi)一行的開(kāi)頭或者結(jié)尾,而不是混在一起帮碰。

<?php

switch (
    $expr1
    && $expr2
) {
    // structure body
}

5.3 while, do while

while 結(jié)構(gòu)如下相味。注意括號(hào),空格和大括號(hào)的位置收毫。

<?php

while ($expr) {
    // structure body
}

括號(hào)中的表達(dá)式 可能 會(huì)被分開(kāi)多行攻走,沒(méi)一行至少要縮進(jìn)一次殷勘。如果這樣做,第一個(gè)條件 必須 在新的一行昔搂。右括號(hào)和左大括號(hào) 必須 在同一行玲销,而且中間有一個(gè)空格。條件中間的布爾控制符 必須 在沒(méi)一行的開(kāi)頭或者結(jié)尾摘符,而不是混在一起贤斜。

<?php

while (
    $expr1
    && $expr2
) {
    // structure body
}

同樣的, do while 申明如下逛裤。注意括號(hào)瘩绒,空格和大括號(hào)的位置。

<?php

do {
    // structure body;
} while ($expr);

括號(hào)中的表達(dá)式 可能 會(huì)被分開(kāi)多行带族,沒(méi)一行至少要縮進(jìn)一次锁荔。如果這樣做,第一個(gè)條件 必須 在新的一行蝙砌。條件中間的布爾控制符 必須 在每一行的開(kāi)頭或者結(jié)尾阳堕,而不是混在一起。

<?php

do {
    // structure body;
} while (
    $expr1
    && $expr2
);

5.4 for

for 申明如下择克。注意括號(hào)恬总,空格和大括號(hào)的位置。

<?php

for ($i = 0; $i < 10; $i++) {
    // for body
}

括號(hào)中的表達(dá)式 可能 會(huì)被分開(kāi)多行肚邢,每一行至少要縮進(jìn)一次壹堰。如果這樣做,第一個(gè)條件 必須 在新的一行骡湖。右括號(hào)和左大括號(hào) 必須 在同一行贱纠,而且中間有一個(gè)空格。

<?php

for (
    $i = 0;
    $i < 10;
    $i++
) {
    // for body
}

5.5 foreach

foreach 語(yǔ)句的寫法如下所示勺鸦。請(qǐng)注意它的圓括號(hào)并巍、空格和花括號(hào)目木。

<?php

foreach ($iterable as $key => $value) {
    // 迭代主體
}

5.6 try 换途, catchfinally

一個(gè) try-catch-finally 模塊包含下面這些內(nèi)容刽射。請(qǐng)注意它的圓括號(hào)军拟、空格和花括號(hào)。

<?php

try {
    // try 主體
} catch (FirstThrowableType $e) {
    // 捕獲異常主體
} catch (OtherThrowableType | AnotherThrowableType $e) {
    // 捕獲異常主體
} finally {
    // finally 主體
}

6. 運(yùn)算符

運(yùn)算符的樣式規(guī)則按元數(shù)分組(其接受的操作數(shù)個(gè)數(shù))誓禁。

當(dāng)運(yùn)算符周圍允許出現(xiàn)空格時(shí)懈息, 可以 出于可讀性目的打多個(gè)空格。

所有這里沒(méi)描述的運(yùn)算符暫不作限定摹恰。

6.1. 一元運(yùn)算符

遞增 / 遞減運(yùn)算符和操作數(shù)之間 不得 有任何空格辫继。

$i++;
++$j;

類型轉(zhuǎn)換運(yùn)算符的圓括號(hào)內(nèi)部 不得 有任何空格:

$intValue = (int) $input;

6.2. 二元運(yùn)算符

所有二進(jìn)制 算術(shù)怒见,比較賦值姑宽,按位遣耍,邏輯字符串類型運(yùn)算符必須在前后跟至少一個(gè)空格:

if ($a === $b) {
    $foo = $bar ?? $a ?? $b;
} elseif ($a > $b) {
    $foo = $a + $b * $c;
}

6.3. 三元運(yùn)算符

條件運(yùn)算符炮车,也稱為三元運(yùn)算符舵变,必須在 ?:這兩個(gè)字符之間:

$variable = $foo ? 'foo' : 'bar';

如果省略條件運(yùn)算符的中間操作數(shù),運(yùn)算符必須遵循與其他二進(jìn)制比較運(yùn)算符相同的樣式規(guī)則:

$variable = $foo ?: 'bar';

7. 閉包(Closures)

閉包聲明時(shí)必須在 function 關(guān)鍵字后留有1個(gè)空格瘦穆,并且在 use 關(guān)鍵字前后各留有1個(gè)空格纪隙。

左花括號(hào)必須跟隨前文寫在同一行,右花括號(hào)必須在函數(shù)體后換行放置扛或。

不能在參數(shù)和變量的左括號(hào)后和右括號(hào)前放置空格绵咱。

不能在參數(shù)和變量的逗號(hào)前放置空格,但必須在逗號(hào)后放置1個(gè)空格熙兔。

閉包參數(shù)如果有默認(rèn)值麸拄,該參數(shù)必須放在參數(shù)列表末尾。

如果聲明了返回類型黔姜,它必須遵循普通函數(shù)和方法相同的規(guī)則;如果使用 use 關(guān)鍵字秆吵,冒號(hào)必須在 use 右括號(hào)后且冒號(hào)前后不能有空格淮椰。

閉包的聲明方式如下,留意括號(hào)纳寂,逗號(hào)主穗,空格和花括號(hào):

<?php

$closureWithArgs = function ($arg1, $arg2) {
    // 函數(shù)體
};

$closureWithArgsAndVars = function ($arg1, $arg2) use ($var1, $var2) {
    // 函數(shù)體
};

$closureWithArgsVarsAndReturn = function ($arg1, $arg2) use ($var1, $var2): bool {
    // 函數(shù)體
};

參數(shù)和變量可以分多行放置,每個(gè)后續(xù)行縮進(jìn)一次毙芜。執(zhí)行此操作時(shí)忽媒,列表中的第一項(xiàng)必須放在下一行,并且每行只能有一個(gè)參數(shù)或變量腋粥。

結(jié)束多行列表(或者參數(shù)晦雨,變量)的時(shí)候,右括號(hào)和左大括號(hào) 必須 要放在一行隘冲,而且中間有一個(gè)空格闹瞧。

下面是有和沒(méi)有多行參數(shù)列表與變量列表的閉包示例。

<?php

$longArgs_noVars = function (
    $longArgument,
    $longerArgument,
    $muchLongerArgument
) {
   // body
};

$noArgs_longVars = function () use (
    $longVar1,
    $longerVar2,
    $muchLongerVar3
) {
   // body
};

$longArgs_longVars = function (
    $longArgument,
    $longerArgument,
    $muchLongerArgument
) use (
    $longVar1,
    $longerVar2,
    $muchLongerVar3
) {
   // body
};

$longArgs_shortVars = function (
    $longArgument,
    $longerArgument,
    $muchLongerArgument
) use ($var1) {
   // body
};

$shortArgs_longVars = function ($arg) use (
    $longVar1,
    $longerVar2,
    $muchLongerVar3
) {
   // body
};

注意格式化規(guī)則也適用一個(gè)閉包在一個(gè)方法或者操作中作為參數(shù)被直接引用展辞。

<?php

$foo->bar(
    $arg1,
    function ($arg2) use ($var1) {
        // body
    },
    $arg3
);

8. 匿名類

匿名類 必須 遵循上面章節(jié)中和閉包一樣的方針和準(zhǔn)則奥邮。

<?php

$instance = new class {};

只要 implements 接口列表不換行,左花括號(hào) 可以 和關(guān)鍵字 class 在同一行。如果接口列表?yè)Q行洽腺,花括號(hào) 必須 放在最后一個(gè)接口的下一行脚粟。

<?php

// 花括號(hào)在同一行
$instance = new class extends \Foo implements \HandleableInterface {
    // 類內(nèi)容
};

// 花括號(hào)在下一行
$instance = new class extends \Foo implements
    \ArrayAccess,
    \Countable,
    \Serializable
{
    // 類內(nèi)容
};
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市蘸朋,隨后出現(xiàn)的幾起案子珊楼,更是在濱河造成了極大的恐慌,老刑警劉巖度液,帶你破解...
    沈念sama閱讀 218,204評(píng)論 6 506
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件厕宗,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡堕担,警方通過(guò)查閱死者的電腦和手機(jī)已慢,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,091評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)霹购,“玉大人佑惠,你說(shuō)我怎么就攤上這事∑敫恚” “怎么了膜楷?”我有些...
    開(kāi)封第一講書人閱讀 164,548評(píng)論 0 354
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)贞奋。 經(jīng)常有香客問(wèn)我赌厅,道長(zhǎng),這世上最難降的妖魔是什么轿塔? 我笑而不...
    開(kāi)封第一講書人閱讀 58,657評(píng)論 1 293
  • 正文 為了忘掉前任特愿,我火速辦了婚禮,結(jié)果婚禮上勾缭,老公的妹妹穿的比我還像新娘揍障。我一直安慰自己,他們只是感情好俩由,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,689評(píng)論 6 392
  • 文/花漫 我一把揭開(kāi)白布毒嫡。 她就那樣靜靜地躺著,像睡著了一般幻梯。 火紅的嫁衣襯著肌膚如雪兜畸。 梳的紋絲不亂的頭發(fā)上,一...
    開(kāi)封第一講書人閱讀 51,554評(píng)論 1 305
  • 那天礼旅,我揣著相機(jī)與錄音膳叨,去河邊找鬼洽洁。 笑死痘系,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的饿自。 我是一名探鬼主播汰翠,決...
    沈念sama閱讀 40,302評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼龄坪,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來(lái)了复唤?” 一聲冷哼從身側(cè)響起健田,我...
    開(kāi)封第一講書人閱讀 39,216評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎佛纫,沒(méi)想到半個(gè)月后妓局,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,661評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡呈宇,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,851評(píng)論 3 336
  • 正文 我和宋清朗相戀三年好爬,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片甥啄。...
    茶點(diǎn)故事閱讀 39,977評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡存炮,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出蜈漓,到底是詐尸還是另有隱情穆桂,我是刑警寧澤,帶...
    沈念sama閱讀 35,697評(píng)論 5 347
  • 正文 年R本政府宣布融虽,位于F島的核電站享完,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏有额。R本人自食惡果不足惜驼侠,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,306評(píng)論 3 330
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望谆吴。 院中可真熱鬧倒源,春花似錦、人聲如沸句狼。這莊子的主人今日做“春日...
    開(kāi)封第一講書人閱讀 31,898評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)腻菇。三九已至胳螟,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間筹吐,已是汗流浹背糖耸。 一陣腳步聲響...
    開(kāi)封第一講書人閱讀 33,019評(píng)論 1 270
  • 我被黑心中介騙來(lái)泰國(guó)打工, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留丘薛,地道東北人嘉竟。 一個(gè)月前我還...
    沈念sama閱讀 48,138評(píng)論 3 370
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親舍扰。 傳聞我的和親對(duì)象是個(gè)殘疾皇子倦蚪,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,927評(píng)論 2 355

推薦閱讀更多精彩內(nèi)容