W3Cschool
恭喜您成為首批注冊用戶
獲得88經(jīng)驗值獎勵
在編寫Hack代碼時,通常會啟動文件<?hh并開始編寫代碼。但是,一個頂線實際上在Typechecker解釋代碼方面非常重要。
Hack文件中的代碼<?hh以其頂部的四個字符開頭,據(jù)說處于部分模式。這意味著typechecker會檢查一下它可以,但不再有; 它不堅持全面覆蓋。部分模式很好用于開始逐漸輸入現(xiàn)有的代碼。以下是部分模式的規(guī)則:
<?hh
namespace Hack\UserDocumentation\TypeChecker\Modes\Examples\Partial;
use \Hack\UserDocumentation\TypeChecker\Modes\Examples\NonHack as NonHack;
// This function isn't type annotated, so callers will be able to do whatever
// they want with its result. However, the typechecker does still look at and
// check the body of the function.
function foo() {
$a = 1;
// This will geneate a type error:
// an int does not allow array append (Typing[4006])
$a[] = 2;
}
class A {
private int $x;
public function __construct() {
$this->x = 9;
}
public function getX(int $y): ?int {
return $y > 4 ? $this->x : null;
}
// You can even have non-type annotated code in the same class as
// type annotated code.
public function notTyped($z) {
return "Hello" . $z;
}
}
function bar(): int {
$a = new A();
// Not typechecked either. So we can pass an int and it will be converted to
// a string by the runtime, luckily.
echo $a->notTyped(3);
// The return value from this call is not typechecked since B is in a PHP
// file -- the typechecker assumes we know what we are doing since the
// annotation is missing.
$b = NonHack\B::getSomeInt();
echo NonHack\php_func(3, $b);
$i = $a->getX($b);
if ($i !== null) {
return $i;
} else {
return 0;
}
}
bar();
Output
string(4) "1004"
Hello33100
請注意,我們已經(jīng)注釋了一些代碼,但不是全部。無論該功能本身的注釋如何,都會檢查推送的代碼。
hack文件為:
<?hh // strict
意味著Typechecker在該文件中強制執(zhí)行嚴(yán)格的輸入規(guī)則。如果在所有可能的情況下,使用嚴(yán)格模式啟動新項目 - 如果代碼庫中的每個文件都處于嚴(yán)格模式,則Typechecker的覆蓋范圍將最大化,因為它將能夠完全檢查所有內(nèi)容,并且在運行時不會出現(xiàn)類型錯誤。
以下是嚴(yán)格模式的規(guī)則:
嚴(yán)格模式的是你想要的模式。整個Typechecker的好處是可以使用的,應(yīng)該確保零運行時類型的錯誤。
<?hh // strict
namespace Hack\UserDocumentation\TypeChecker\Modes\Examples\Strict;
use \Hack\UserDocumentation\TypeChecker\Modes\Examples\NonHack as NonHack;
function foo(): void {
$a = 1;
// This will generate a type error:
// an int does not allow array append (Typing[4006])
$a[] = 2;
}
class A {
private int $x;
public function __construct() {
$this->x = 9;
}
public function getX(int $y): ?int {
return $y > 4 ? $this->x : null;
}
// In partial, this didn't have to be annotated. In strict, it does.
public function notTyped(string $z): string {
return "Hello" . $z;
}
}
function bar(): int {
$a = new A();
// This is typechecked, so we can't pass an string-y int; we must pass a
// string
echo $a->notTyped("3");
// Cannot call these in strict mode:
// Unbound name:
// Hack\UserDocumentation\TypeChecker\Modes\Examples\NonHack\B
// (an object type) (Naming[2049])
$b = NonHack\B::getSomeInt();
// Unbound name:
// Hack\UserDocumentation\TypeChecker\Modes\Examples\NonHack\php_func
// Typing[4107])
echo NonHack\php_func(3, $b);
$i = $a->getX(100);
if ($i !== null) {
return $i;
} else {
return 0;
}
}
// This can't be in strict mode either. You need to put this in partial file
// and include it from this file. For the purposes of this example, though,
// we'll just suppress the error.
/* HH_FIXME[1002] So we can get interesting type-checking errors */
bar();
Output
string(4) "1004"
Hello33100
請注意,我們不能再調(diào)用該<?php文件,并且Hack文件中的所有實體都被注釋。
hack代碼為:
<?hh // decl
處于聲明模式。聲明模式代碼沒有類型檢查。然而,提取了在decl模式下的函數(shù),類等的簽名,并且在檢查其他代碼時被Typechecker使用。在轉(zhuǎn)換使用PHP編寫的代碼時,聲明模式是最有用的:雖然該代碼的正文可能具有您不想立即處理的類型錯誤,但仍然有益于使該代碼的簽名,至少其唯一存在,對其他代碼可見。事實上,Hack的一個非?;镜倪w移路徑是將所有<?php文件更改為decl模式,然后逐個開始采取每個文件并使其部分。
新的hack代碼應(yīng)該永遠寫在DECL模式。
<?hh // decl
// Before this was <?php code. Now the typechecker can see the signatures of
// these functions and classes for when Hack calls them, even in strict mode.
namespace Hack\UserDocumentation\TypeChecker\Modes\Examples\Decl;
function php_func($x, $y) {
return $x . $y;
}
class B {
static function getSomeInt() {
return 100;
}
}
<?hh // strict
namespace Hack\UserDocumentation\TypeChecker\Modes\Examples\CallIntoDecl;
require __DIR__ . '/decl.inc.php';
// This actually makes the call to calling_into_decl() since we cannot have
// top level functions in strict mode
use \Hack\UserDocumentation\TypeChecker\Modes\Examples\Decl as Decl;
function calling_into_decl(): string {
// If php_func wasn't in decl mode, then we would get an unbound name error.
// As it is, we can call this function and the typechecker will ensure we are
// passing in the right number of arguments, but not the types of them.
return Decl\php_func("a", "b");
}
<?hh
namespace Hack\UserDocumentation\TypeChecker\Modes\Examples\CallIntoDecl;
var_dump(calling_into_decl());
Output
string(2) "ab"
該示例顯示所有三種模式。首先,它顯示一個以前存在的聲明模式文件<?php。除了標(biāo)題更改之外,沒有添加任何其他內(nèi)容。然后它顯示一個嚴(yán)格的模式文件調(diào)用到declare文件。Typechecker知道函數(shù)和類的簽名,并且可以確?;镜臇|西,例如是否調(diào)用命名實體并傳遞正確數(shù)量的參數(shù)。最后,我們有一個部分模式文件實際上以嚴(yán)格模式調(diào)用該函數(shù),因為我們不能在嚴(yán)格模式下進行頂層函數(shù)調(diào)用。
如上例所示,模式可以自由混合; 您的項目中的每個文件可以處于不同的Typechecker模式。
Copyright©2021 w3cschool編程獅|閩ICP備15016281號-3|閩公網(wǎng)安備35020302033924號
違法和不良信息舉報電話:173-0602-2364|舉報郵箱:jubao@eeedong.com
掃描二維碼
下載編程獅App
編程獅公眾號
聯(lián)系方式:
更多建議: