在查看laravel源碼的時(shí)候擅笔,看到有如下一段代碼:
/**
* Get the registered service provider instance if it exists.
*
* @param \Illuminate\Support\ServiceProvider|string $provider
* @return \Illuminate\Support\ServiceProvider|null
*/
public function getProvider($provider)
{
$name = is_string($provider) ? $provider : get_class($provider);
return Arr::first($this->serviceProviders, function ($key, $value) use ($name) {
return $value instanceof $name;
});
}
當(dāng)時(shí)就有點(diǎn)困惑,然后在tinker連就敲了一下驗(yàn)證汹押,結(jié)果陷入更大的迷惑中矿筝。。棚贾。
下棉代碼是這個(gè)問(wèn)題的嘗試的心路歷程:
>>> use App\Model\Account;
=> null
>>> $account = new Account();
=> App\Model\Account {#1607}
>>> $account instanceof 'App\Model\Account';
PHP Parse error: Syntax error, unexpected T_CONSTANT_ENCAPSED_STRING on line 1
>>> $account instanceof App\Model\Account;
=> true
>>> $a = 'abc';
=> "abc"
>>> $a instanceof 'abc';
PHP Parse error: Syntax error, unexpected T_CONSTANT_ENCAPSED_STRING on line 1
>>> $account instanceof 'App\Model\Account';
PHP Parse error: Syntax error, unexpected T_CONSTANT_ENCAPSED_STRING on line 1
>>> get_class($a);
PHP warning: get_class() expects parameter 1 to be object, string given on line 1
>>> get_class($account);
=> "App\Model\Account"
>>> $name = get_class($account);
=> "App\Model\Account"
>>> $account instanceof $name;
=> true
>>> gettype($name);
=> "string"
>>> $account instanceof "App\Model\Account";
PHP Parse error: Syntax error, unexpected T_CONSTANT_ENCAPSED_STRING on line 1
>>> $account instanceof Account;
=> true
>>> $temp = "App\Model\Account";
=> "App\Model\Account"
>>> $account instanceof $temp;
=> true
其實(shí)上面問(wèn)題的核心是instanceof的用法問(wèn)題窖维,在網(wǎng)上已經(jīng)有這樣的討論,我將其粘貼出來(lái):
class MyClass {
public $bar;
public function __construct() {
$this->bar = "Hello World";
}
public function foo() {
return $this->bar;
}
}
$a = new MyClass;
$b = new MyClass;
if($a instanceof get_class($b)) {
echo "Is instance";
} else {
echo "Is NOT instance";
}
//輸出
Parse error: syntax error, unexpected '(' in /usercode/file.php on line 19
但是如果妙痹,你這樣改寫:
$x = get_class($b);
if($a instanceof $x) {
echo "Is instance";
} else {
echo "Is NOT instance";
}
//輸出
Is instance
答案是因?yàn)閕nstanceof并不是函數(shù)铸史,只能接受對(duì)象(字面量的,不是字符串)或者變量怯伊。如果后面接的是函數(shù)或者是字符串(字面量的)琳轿,那肯定是會(huì)報(bào)錯(cuò)的,本身語(yǔ)法就會(huì)有問(wèn)題。
原討論的回答如下:
Logically that would be the case, and if instanceof were a function then it would be the actual case. However, instanceof is a language construct operator, not a normal function and for that reason it doesn't play by the same rules.
instanceof does not accept expressions like a normal function would, and because calling a function like get_class is an expression you can't use it with instanceof.
instanceof accepts only two types of arguments. Either a class name (literal, not as a string) or a variable containing a string that is the class name.
Other language constructs like empty and isset function in exactly the same fashion (ie: you can't pass an expression to them either).
Note that you can use the is_a() function if you want to pass the class name as an expression.
參考網(wǎng)站: