选择表中的最后一行


163

我想检索插入到表中的最后一个文件。我知道该方法first()存在,并为您提供表中的第一个文件,但我不知道如何获取最后一个插入。


另请参见stackoverflow.com/questions/33321447/…如何对现有关系进行排序(hasMany)
Tarek Adam

这适用于任何询问和回答Laravel的人。请记住,指定要使用的Laravel版本非常重要。通常,版本4和5与以前的版本有所不同。
Heroselohim

Answers:


224

您需要按与现在要订购的相同字段进行订购,但要递减。例如,如果您在上传完成时有一个时间戳记upload_time,您将执行以下操作;

对于Pre-Laravel 4

return DB::table('files')->order_by('upload_time', 'desc')->first();

对于Laravel 4及更高版本

return DB::table('files')->orderBy('upload_time', 'desc')->first();

对于Laravel 5.7及更高版本

return DB::table('files')->latest('upload_time')->first();

这将按上载时间,降序对文件表中的行进行排序,并采用第一个。这将是最新上传的文件。


15
对于Laravel 4,这应该是orderBy,而不是order_by
Jared Eitnier 2013年

9
当您使用ORM时,这是一种正确的方法:User::orderby('created_at', 'desc')->first();
Cas Bloem 2014年

1
Laravel 5.x =orderBy('created_at', 'desc')
0x1ad2 '16

9
为什么要使用created_at列?使用主键ID的速度要快得多。Laravel 5.x Files::orderBy(id', 'desc')->first();按日期排序的工作时间更长,因为日期是字符串并且很可能没有索引。虽然主键已编入索引并且可以超快速地工作。即使created_at已建立索引,它也是已建立索引的字符串,如果是primary,则不是INT。索引字符串的性能较差。
KorbenDallas'4

4
@KorbenDallas评论应该是答案,因为有时orderBy('created_at', 'desc')没有给您最后一行。示例:3行可以具有完全相同的TIMESTAMP值,并且orderBy('created_at', 'desc')您将获得3行中的第一个(不一定是最后一行)
viery365 '18

111

开箱即用,使用Laravel提供的最新范围。

Model::latest()->first();

这样,您就不会检索所有记录。一个更好的orderBy快捷方式。


7
请注意,此方法使用模型中的自动生成的created_at($timestamps = true),但可以随意禁用,因此如果未定义
则会

我正在使用Laravel 5.7,尝试在Model上执行此操作仍会为我检索所有记录。
CJ丹尼斯

1
请注意,如果您在同一秒内添加了多个记录,则这些记录的created_at时间将相同,因此,latest()返回的记录可能与您期望的记录不同。
F3CP '19

请注意,您不需要'created_at'列。您可以从哪个列中指定最新的。例如:Model :: latest('dateColumn')-> first();
汤姆(Tom)

如果在1秒钟内插入两行,则可能无法获得实际的最后一行(实际上是在单元测试中引起的问题)。
辣椒

75

您从未提到过您是否在使用Laravel的默认ORM Eloquent。假设您希望通过created_at获取User表的最新条目,则可以执行以下操作:

User::orderBy('created_at', 'desc')->first();

首先,它按created_at字段降序对用户排序,然后获取结果的第一条记录。

这将返回您一个User对象的实例,而不是一个集合。当然,要使用此替代方法,您必须拥有一个User模型,扩展了Eloquent类。这听起来可能有点令人困惑,但是起步确实很容易,ORM确实很有帮助。

有关更多信息,请查看功能丰富且详细的官方文档


42

获取最后的记录详细信息

  1. Model::all()->last(); 要么
  2. Model::orderBy('id', 'desc')->first();

获取最后的记录ID

  1. Model::all()->last()->id; 要么
  2. Model::orderBy('id', 'desc')->first()->id;

14

Laravel集合具有方法last

Model::all() -> last(); // last element 
Model::all() -> last() -> pluck('name'); // extract value from name field. 

这是最好的方法。


16
只是想指出,该all()方法实际上加载了所有项目。这在具有数百万条记录的表上将不起作用。
史蒂芬·杰弗里斯

1
除了史蒂芬·杰弗里斯(Steven Jeffries)的评论外,我想指出的是,调用last()返回单个Eloquent实例而不是Collection,并且调用pluck()等于Model::all()->pluck('name')返回,因此返回表name所有行的属性
ivcandela

5
这种方法实际上更糟。您正在使用PHP执行而不是作为数据库级别来获取最后的原始数据。如果表有数百万个原始数据,那您会知道效率低了多少呢?
Bhaskar Dabhi

这是最好的方法。-不!从来没有,永远不会。您将加载所有行,而不仅仅是需要的行。
勒内·罗斯

11

试试这个 :

Model::latest()->get();

1
这将返回多行。他需要一行。first()将通过orderBy()子句帮助他。
塔希尔·阿弗里迪

如果在1秒钟内插入两行,则可能无法获得实际的最后一行(实际上是在单元测试中引起的问题)。
辣椒

1
在大表上,这将导致内存不足异常,因为正如@TahirAfridi所述,这会将所有行加载到内存中。
Rihards

6

您可以将Laravel提供的最新范围与您要过滤的字段一起使用,假设它将按ID排序,然后:

Model::latest('id')->first();

因此,通过这种方式,您可以避免created_at在Laravel默认情况下按字段排序。


5

要获取最后的记录详细信息,请使用以下代码:

Model::where('field', 'value')->get()->last()

不要使用它。这是一个非常不好的做法,它的作用域为latest(),它提供对最后插入的行的直接访问。
工作猪

3

在Laravel 6.x中另一种花哨的方法可以做到这一点(虽然不确定,但也必须在5.x下工作):

DB::table('your_table')->get()->last();

您也可以访问字段:

DB::table('your_table')->get()->last()->id;


在Laravel 5.8中对我也有效,在看到您的答案之前便已发布答案
Dazzle

1
关于laravel如何在后台执行此操作以及为什么这样做get()会对大数据集造成危险的一些解释,method将从中获取所有内容your_table并生成Collection,并且last()method将从该collection中获取最后一个项目。因此,您已经将表中的所有数据加载到了内存中(坏)。您应该只在后台执行`orderBy($ column,'desc')`并获取第一条记录。
Anuj Shrestha


1

如果您要在对新模型执行savecreate操作时查找刚刚在Laravel 3和4中插入的实际行,例如:

$user->save();

-要么-

$user = User::create(array('email' => 'example@gmail.com'));

那么插入的模型实例将被返回,并可用于进一步的操作,例如重定向到刚创建的用户的个人资料页面。

在低容量系统上查找最后插入的记录几乎可以一直使用,但是如果您必须同时插入插入内容,则可能最终查询以查找错误的记录。在需要更新多个表的事务系统中,这确实可能成为问题。


1

在laravel 5.3中,以上所有内容似乎都不适合我,因此我使用以下方法解决了自己的问题:

Model::where('user_id', '=', $user_id)->orderBy('created_at', 'desc')->get();

希望能够保释某人。


1

使用Model::where('user_id', $user_id)->latest()->get()->first(); 它只会返回一条记录,如果找不到,它将返回null。希望这会有所帮助。


0

User::orderBy('created_at', 'desc')->first();我认为,如果表格中有日期字段,则this()是最佳解决方案。但是Model ::orderBy('id', 'desc')->first()->id;,我确定没有日期字段,这是最好的解决方案。


0

请注意,如果要查找顺序记录或事件/有序记录last()latest()则不确定。最后/最近的记录可以具有完全相同的created_at时间戳记,您获得的时间戳记并不确定。也是orderBy(id|foo)->first()。欢迎其他有关如何确定性的想法/建议。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.