如何在 Django 项目中添加分页?
分页系统是博客、搜索引擎、结果列表等中最常见的功能之一。看到分页系统的流行,django 开发者构建了一个Paginator 类,这样web 开发者就不必考虑制作分页器的逻辑。
分页器类位于 django/core/paginator.py 中。所以要使用 Paginator 类,我们首先需要从django.core.paginator导入它
from django.core.paginator import Paginator
句法 :
p = Paginator(list_of_objects, no_of_objects_per_page)
第一个参数是将分布在页面上的对象列表。第二个参数表示将在每页上显示的对象数。这两个参数是必需的。
然而,分页器类还有两个可选参数,如下所列——
- orphans——它的值必须是一个小于 no_of_objects_per_page 值的整数。它告诉最后一页是否有最少数量的对象。如果最后一页中剩余对象的数量小于或等于此参数的值,则这些对象将添加到前一页。默认值为 0。
- allow_empty_first_page – 它采用布尔值。是否允许第一页为空。
注意:第一个参数不必是列表。相反,它可以是一个元组、查询集或其他带有 count() 或 __len__() 方法的可切片对象。
如何使用分页器类?
假设我们正在开发一个博客网站。我们在 models.py 中定义了 Post 模型,我们已经创建了 8 个这样的帖子。现在在views.py中,我们编写了以下代码——
Python3
from django.shortcuts import render
from .models import Post
from django.core.paginator import Paginator
# Create your views here.
def index(request):
posts = Post.objects.all() # fetching all post objects from database
p = Paginator(posts, 5) # creating a paginator object
# getting the desired page number from url
page_number = request.GET.get('page')
try:
page_obj = p.get_page(page_number) # returns the desired page object
except PageNotAnInteger:
# if page_number is not an integer then assign the first page
page_obj = p.page(1)
except EmptyPage:
# if page is empty then return last page
page_obj = p.page(p.num_pages)
context = {'page_obj': page_obj}
# sending the page object to index.html
return render(request, 'index.html', context)
HTML
Django Paginator example
{% for post in page_obj.object_list %}
{# note that the list of posts are in the page_obj.object_list not page_obj #}
{{post.title}}
{{post.author}}
{{post.content}}
{% endfor %}
{%if page_obj.has_previous %} {# whether the previous page exists #}
< {# link to the prev page #}
{% endif %}
{{page_obj.number}} {# the current page number #}
{%if page_obj.has_next %} {# whether the next page exists #}
> {# link to the next page #}
{% endif %}
在第三行,导入了分页器类。在 index函数中,我们构造了一个名为 p 的分页器对象。这个分页器创建页面对象。每个 Page 对象将具有相同数量的帖子对象。然后我们从 GET 请求的查询参数“page”中检索所需的页码。此页码用于提取正确的页面对象。
现在在 index.html –
HTML
Django Paginator example
{% for post in page_obj.object_list %}
{# note that the list of posts are in the page_obj.object_list not page_obj #}
{{post.title}}
{{post.author}}
{{post.content}}
{% endfor %}
{%if page_obj.has_previous %} {# whether the previous page exists #}
< {# link to the prev page #}
{% endif %}
{{page_obj.number}} {# the current page number #}
{%if page_obj.has_next %} {# whether the next page exists #}
> {# link to the next page #}
{% endif %}
结果 :
在图像中,我们通过 GET 请求(用矩形表示)发送了页码的值。您可以在图像底部看到分页(用矩形标记)。
这是最后一页的另一张图片——
方法 : It takes a number argument and returns a Page object with the given 1-based index. If the passed argument is not a number then it returns the first page. If the page number is negative or a number that is greater than the number of pages then it returns the last page. Throws EmptyPage error if the object list of the page is empty and allow_empty_first_page is set to false in Paginator object.Paginator.get_page( page_number ) Paginator.page(number) It also does the same thing but raises InvalidPage error if the page of that number does not exist.
属性 :Paginator.count returns the total number of objects across all pages. Paginator.num_pages returns the total number of pages Paginator.page_range returns a 1-based range iterator
但是,由于Paginator类使用Page类来分发对象,如果我们对Page类多一些了解就更好了。
页面类:
通常 Page 对象用于分页器类中。您很少需要手动构建它。
语法:
page = Page( object_list , number, paginator)
这里的对象列表是对象列表,number 参数用于对 Page 对象进行编号。分页器是为其构造此页面对象的分页器对象。
属性 :Page.object_list returns the list of objects Page.number returns the number of the page object Page.paginator returns the corresponding paginator object
方法 : Page.has_next() returns True if the next Page object exits else returns False Page.has_previous() returns True if the previous Page object exits else returns False Page.has_other_pages() Returns True if there’s a next or previous page. Page.next_page_number() Returns the next page number. Raises InvalidPage if next page doesn’t exist. Page.previous_page_number() Returns the previous page number. Raises InvalidPage if previous page doesn’t exist. Page.start_index() Returns the 1-based index of the first object on the page, relative to all of the objects in the paginator’s lis Page.end_index() Returns the 1-based index of the last object on the page, relative to all of the objects in the paginator’s list.