在拉拉维尔模型中,$this->产品和$this->产品()有什么区别?



我从getReward1getReward2得到了不同的结果:

:

class User extends Authenticatable
{
public function Products()
{
return $this->hasMany('AppProduct', 'user_id');
}
public function getReward1()
{
return $this
->Products
->where('reward', '>', 0)
->where('status', 0)
->sum('reward'); // sum = 7,690,000
}
public function getReward2()
{
return $this
->Products()
->where('reward', '>', 0)
->where('status', 0)
->sum('reward'); // sum = 7,470,000
}
}

getReward1返回7,690,000,getReward2返回7,470,000(两个不同的值)

$this->Products$this->Products()有什么不同?

$this->products; 
// Returns a Collection
$this->products(); 
// Returns a Relation instance, which is a query builder and can be of type HasMany, BelongsTo...
$this->products()->get(); 
// Is EXACTLY like doing $this->products for the first time. 

主要区别在于products()只是一个尚未执行的查询,而products是该查询的实际结果。

老实说,即使名字相同,可能会让人混淆,但它们之间没有其他相似之处。

一个简单的类比:

DB::table('products')->where('user_id', 18); //could be the $user->products()
DB::table('products')->where('user_id', 18)->get(); //could be $user->products

这只是一个类比,内部并不完全是这样,但是你明白了。

为了增加更多的混乱,集合方法通常与你在查询中找到的方法相似;都有where(),first()

要记住的主要事情是,使用括号,您仍然在构建查询。在调用getfirst之前,您一直处于查询生成器中。

没有,你已经有了你的结果,你是在一个集合(https://laravel.com/docs/8.x/collections)。


关于getReward1getReward2之间的差异,如果没有看到数据库结构,很难确切地知道发生了什么。

它可以是很多东西,但是当你调用sum方法时,你是在getReward1的Collection实例上调用它,在getReward2的查询生成器上调用它(你实际上是在用SELECT SUM(reward)...执行查询)。

$this->Products()将返回查询生成器的一个实例。随后的where子句将约束DB查询,然后只返回您想要的产品。这些将不会存储在模型实例中。

$this->Products将从DB中获取所有产品,并将它们作为Eloquent Collection存储在模型实例中。随后的where子句将在Eloquent Collection上执行。

本质上,方法在DB中做所有的事情,然而,属性是获取所有的行,然后用PHP限制它。

相关内容

最新更新