当前位置:首页>python>深入理解Python迭代:更高效的循环方式

深入理解Python迭代:更高效的循环方式

  • 2026-03-27 05:44:07
深入理解Python迭代:更高效的循环方式

Python自学手册

Pythonfor循环与其他语言中的for循环工作方式不同。在本文中,我们将深入探讨Pythonfor循环,了解其底层工作原理以及为何会以这种方式工作。

循环陷阱

我们将从一些陷阱开始我们的探索。在了解了Python中循环的工作原理后,我们会重新审视这些陷阱,并解释其中的原因。

陷阱1:循环两次

假设我们有一个数字列表和一个生成器,该生成器会返回这些数字的平方:

python>>> numbers = [1, 2, 3, 5, 7]>>> squares = (n**2 for n in numbers)

我们可以将生成器对象传入元组构造函数,将其转换为元组:

python>>> tuple(squares)(1, 4, 9, 25, 49)

如果我们再将同一个生成器对象传入sum函数,可能会期望得到这些数字的和,即88

python>>> sum(squares)0

但实际上我们得到的是0

陷阱2:包含性检查

我们使用同样的数字列表和生成器对象:

python>>> numbers = [1, 2, 3, 5, 7]>>> squares = (n**2 for n in numbers)

如果我们询问9是否在生成器squares中,Python会告诉我们9在其中。但如果我们再次询问同样的问题,Python会告诉我们9不在其中。

python>>> 9 in squaresTrue>>> 9 in squaresFalse

我们两次问了同样的问题,却得到了两个不同的答案。

陷阱3:解包

这个字典包含两个键值对:

python>>> counts = {'apples': 2, 'oranges': 1}

让我们使用多重赋值解包这个字典:

python>>> x, y = counts

你可能会期望解包字典时,会得到键值对,或者可能会报错。

但解包字典既不会报错,也不会返回键值对。解包字典时,你得到的是键:

python>>> x'apples'

在了解了驱动这些Python代码片段的底层逻辑后,我们会回到这些陷阱上来。

回顾:Pythonfor循环

Python没有传统的for循环。为了解释我的意思,让我们看看另一种编程语言中的for循环。

这是用JavaScript编写的传统C风格for循环:

javascriptlet numbers = [1, 2, 3, 5, 7];for (let i = 0; i < numbers.length; i += 1) {print(numbers[i])}

JavaScriptCC++JavaPHP以及许多其他编程语言都有这种类型的for循环。但Python没有。

Python没有传统的C风格for循环。我们确实有一个在Python中被称为for循环的东西,但它的工作方式类似于foreach循环。

这是Python风格的for循环:

pythonnumbers = [1, 2, 3, 5, 7]for n in numbers:print(n)

与传统的C风格for循环不同,Pythonfor循环没有索引变量。没有索引初始化、边界检查或索引递增操作。Pythonfor循环会为我们完成遍历数字列表的所有工作。

因此,虽然Python中有for循环,但它并不是传统的C风格for循环。我们称之为for循环的东西,工作方式完全不同。

定义:可迭代对象与序列

现在我们已经解决了Python中无索引for循环的问题,接下来让我们明确一些定义。

可迭代对象(iterable)是指在Python中可以用for循环遍历的任何东西。可迭代对象可以被遍历,任何可以被遍历的东西都是可迭代对象。

pythonfor item in some_iterable:print(item)

序列(sequence)是一种非常常见的可迭代对象。列表、元组和字符串都是序列。

python>>> numbers = [1, 2, 3, 5, 7]>>> coordinates = (4, 5, 7)>>> words = "hello there"

序列是具有特定特性集的可迭代对象。它们可以从0开始索引,到序列长度减1结束,它们有长度,并且可以切片。列表、元组、字符串和所有其他序列都以这种方式工作。

python>>> numbers[0]1>>> coordinates[2]7>>> words[4]'o'

Python中有很多东西是可迭代对象,但并非所有可迭代对象都是序列。集合、字典、文件和生成器都是可迭代对象,但它们都不是序列。

python>>> my_set = {1, 2, 3}>>> my_dict = {'k1': 'v1', 'k2': 'v2'}>>> my_file = open('some_file.txt')>>> squares = (n**2 for n in my_set)

因此,任何可以用for循环遍历的东西都是可迭代对象,序列是可迭代对象的一种,但Python还有许多其他类型的可迭代对象。

Pythonfor循环不使用索引

你可能会认为,在底层,Pythonfor循环使用索引进行遍历。这里我们使用while循环和索引手动遍历一个可迭代对象:

pythonnumbers = [1, 2, 3, 5, 7]i = 0while i < len(numbers):print(numbers[i])i += 1

这对列表有效,但对所有东西都无效。这种循环方式只适用于序列。

如果我们尝试使用索引手动遍历一个集合,会得到一个错误:

python>>> fruits = {'lemon', 'apple', 'orange', 'watermelon'}>>> i = 0>>> while i < len(fruits):... print(fruits[i])... i += 1...Traceback (most recent call last):File "<stdin>", line 2, in <module>TypeError: 'set' object does not support indexing

集合不是序列,因此它们不支持索引。

我们不能在Python中使用索引手动遍历所有可迭代对象。对于非序列类型的可迭代对象,这种方式根本不起作用。

迭代器驱动for循环

因此,我们已经看到,Pythonfor循环在底层肯定没有使用索引。相反,Pythonfor循环使用迭代器(iterator)。

迭代器是驱动可迭代对象的核心。你可以从任何可迭代对象中获取迭代器。并且你可以使用迭代器手动遍历它所来自的可迭代对象。

让我们看看这是如何工作的。

这里有三个可迭代对象:一个集合、一个元组和一个字符串。

python>>> numbers = {1, 2, 3, 5, 7}>>> coordinates = (4, 5, 7)>>> words = "hello there"

我们可以使用Python的内置iter函数,向每个可迭代对象请求一个迭代器。无论我们处理的是哪种类型的可迭代对象,将其传入iter函数总会返回一个迭代器。

python>>> iter(numbers)<set_iterator object at 0x7f2b9271c860>>>> iter(coordinates)<tuple_iterator object at 0x7f2b9271ce80>>>> iter(words)<str_iterator object at 0x7f2b9271c860>

一旦我们有了迭代器,我们唯一能做的就是通过将其传入内置next函数来获取它的下一个元素。

python>>> numbers = [1, 2, 3]>>> my_iterator = iter(numbers)>>> next(my_iterator)1>>> next(my_iterator)2

迭代器是有状态的,这意味着一旦你从它们中消费了一个元素,这个元素就消失了。

如果你向迭代器请求下一个元素,但已经没有更多元素了,你会得到一个StopIteration异常:

python>>> next(iterator)3>>> next(iterator)Traceback (most recent call last):File "<stdin>", line 1, in <module>StopIteration

因此,你可以从每个可迭代对象中获取迭代器。并且你唯一能对迭代器做的事情,就是使用next函数请求它的下一个元素。如果你将迭代器传入next函数,但它没有下一个元素,就会抛出StopIteration异常。

“Hello Kitty PEZ糖果盒

Hello Kitty PEZ糖果盒照片由Deborah Austin拍摄 知识共享署名许可

你可以将迭代器想象成一个无法重新装填的Hello Kitty PEZ糖果盒。你可以取出糖果,但一旦糖果被取出就无法放回,一旦糖果盒空了,它就没用了。

不使用for循环实现循环

现在我们已经了解了迭代器以及iternext函数,我们将尝试不使用for循环,手动遍历一个可迭代对象。

我们将尝试把这个for循环转换为while循环:

pythondef funky_for_loop(iterable, action_to_do):for item in iterable:action_to_do(item)

为了实现这一点,我们将:

1.从给定的可迭代对象中获取一个迭代器

2.反复从迭代器中获取下一个元素

3.如果成功获取到下一个元素,执行for循环的主体

4.如果在获取下一个元素时得到StopIteration异常,停止循环

pythondef funky_for_loop(iterable, action_to_do):iterator = iter(iterable)done_looping = Falsewhile not done_looping:try:item = next(iterator)except StopIteration:done_looping = Trueelse:action_to_do(item)

我们刚刚通过while循环和迭代器重新发明了for循环。

上面的代码基本上定义了Python中循环的底层工作方式。如果你理解内置iternext函数在遍历事物时的工作方式,你就理解了Pythonfor循环是如何工作的。

事实上,你理解的不仅仅是Pythonfor循环的工作方式。所有遍历可迭代对象的方式都是这样工作的。

迭代器协议(iterator protocol)是“Python中如何遍历可迭代对象的一种专业说法。它本质上定义了Pythoniternext函数的工作方式。Python中的所有迭代形式都由迭代器协议驱动。

for循环使用迭代器协议(正如我们已经看到的):

pythonfor n in numbers:print(n)

多重赋值也使用迭代器协议:

pythonx, y, z = coordinates

星号表达式使用迭代器协议:

pythona, b, *rest = numbersprint(*numbers)

许多内置函数也依赖于迭代器协议:

pythonunique_numbers = set(numbers)

Python中任何与可迭代对象相关的操作,大概率都以某种方式使用了迭代器协议。每当你在Python中遍历一个可迭代对象时,你都在依赖迭代器协议。

生成器是迭代器

所以你可能会想:迭代器看起来很酷,但它们似乎也只是一个实现细节,作为Python用户,我们可能不需要关心它们。

我要告诉你一个消息:在Python中直接使用迭代器是非常常见的。

这里的squares对象是一个生成器:

python>>> numbers = [1, 2, 3]>>> squares = (n**2 for n in numbers)

而生成器是迭代器,这意味着你可以对生成器调用next函数来获取它的下一个元素:

python>>> next(squares)1>>> next(squares)4

但如果你以前使用过生成器,你可能知道你也可以遍历生成器:

python>>> squares = (n**2 for n in numbers)>>> for n in squares:... print(n)...149

如果在Python中你可以遍历某个东西,那么它就是一个可迭代对象。

所以生成器是迭代器,但生成器也是可迭代对象。这是怎么回事?

我之前骗了你

所以当我之前解释迭代器的工作方式时,我忽略了一个关于它们的重要细节。

迭代器是可迭代对象。

我再重复一遍:Python中的每个迭代器也是一个可迭代对象,这意味着你可以遍历迭代器。

因为迭代器也是可迭代对象,所以你可以使用内置iter函数从迭代器中获取迭代器:

python>>> numbers = [1, 2, 3]>>> iterator1 = iter(numbers)>>> iterator2 = iter(iterator1)

记住,当我们对可迭代对象调用iter函数时,它会给我们返回一个迭代器。

当我们对迭代器调用iter函数时,它总会返回它自己:

python>>> iterator1 is iterator2True

迭代器是可迭代对象,并且所有迭代器都是它们自己的迭代器。

pythondef is_iterator(iterable):return iter(iterable) is iterable

是不是有点困惑?

让我们回顾一下这些术语。

可迭代对象是你能够遍历的东西。迭代器是实际执行遍历可迭代对象操作的代理

此外,在Python中,迭代器也是可迭代对象,并且它们作为自己的迭代器。

所以迭代器是可迭代对象,但它们没有某些可迭代对象所具有的多种特性。

迭代器没有长度,也不能被索引:

python>>> numbers = [1, 2, 3, 5, 7]>>> iterator = iter(numbers)>>> len(iterator)TypeError: object of type 'list_iterator' has no len()>>> iterator[0]TypeError: 'list_iterator' object is not subscriptable

从我们Python程序员的角度来看,你能对迭代器做的唯一有用的事情,就是将其传入内置next函数或遍历它:

python>>> next(iterator)1>>> list(iterator)[2, 3, 5, 7]

如果我们第二次遍历迭代器,我们将什么也得不到:

python>>> list(iterator)[]

你可以将迭代器视为一次性的惰性可迭代对象,这意味着它们只能被遍历一次。

对象

可迭代?

迭代器?

可迭代对象

✔️

迭代器

✔️

✔️

生成器

✔️

✔️

列表

✔️

正如你在上面的真值表中看到的,可迭代对象并不总是迭代器,但迭代器总是可迭代对象。

完整的迭代器协议

让我们从Python的角度定义迭代器的工作方式。

可迭代对象可以被传入iter函数,以获取其对应的迭代器。

迭代器:

可以被传入next函数,该函数会返回其下一个元素;如果没有更多元素,则抛出StopIteration异常

可以被传入iter函数,并且会返回其自身

这些陈述的逆命题也成立:

任何可以被传入iter函数而不抛出TypeError异常的东西都是可迭代对象

任何可以被传入next函数而不抛出TypeError异常的东西都是迭代器

任何被传入iter函数时返回自身的东西都是迭代器

这就是Python中的迭代器协议。

迭代器实现惰性求值

迭代器允许我们使用和创建惰性可迭代对象”——这种对象在你请求其下一个元素之前,不会执行任何操作。因为我们可以创建惰性可迭代对象,所以我们可以创建无限长的可迭代对象。并且我们可以创建节省系统资源的可迭代对象,它们可以为我们节省内存和CPU时间。

迭代器无处不在

你在Python中已经见过很多迭代器了。我已经提到过生成器是迭代器。Python的许多内置类也是迭代器。例如,Pythonenumeratereversed对象都是迭代器。

python>>> letters = ['a', 'b', 'c']>>> e = enumerate(letters)>>> e<enumerate object at 0x7f112b0e6510>>>> next(e)(0, 'a')

Python 3中,zipmapfilter对象也是迭代器。

python>>> numbers = [1, 2, 3, 5, 7]>>> letters = ['a', 'b', 'c']>>> z = zip(numbers, letters)>>> z<zip object at 0x7f112cc6ce48>>>> next(z)(1, 'a')

Python中的文件对象也是迭代器。

python>>> next(open('hello.txt'))'hello world\n'

Python的内置函数、标准库和第三方Python库中都有很多迭代器。这些迭代器都像惰性可迭代对象一样工作,将操作延迟到你请求其下一个元素的那一刻。

创建自己的迭代器

了解你已经在使用迭代器是很有用的,但我还希望你知道,你可以创建自己的迭代器和自己的惰性可迭代对象。

这个类创建了一个迭代器,它接收一个数字可迭代对象,并在被遍历时提供每个数字的平方。

pythonclass square_all:def __init__(self, numbers):self.numbers = iter(numbers)def __next__(self):return next(self.numbers) ** 2def __iter__(self):return self

但在我们开始遍历这个类的实例之前,不会执行任何操作。

这里我们有一个无限长的可迭代对象count,你可以看到square_all接收count,而不需要完全遍历这个无限长的可迭代对象:

python>>> from itertools import count>>> numbers = count(5)>>> squares = square_all(numbers)>>> next(squares)25>>> next(squares)36

这个迭代器类是有效的,但我们通常不会以这种方式创建迭代器。通常,当我们想要创建自定义迭代器时,我们会创建一个生成器函数:

pythondef square_all(numbers):for n in numbers:yield n**2

这个生成器函数与我们上面创建的类等价,并且工作方式基本相同。

那个yield语句可能看起来很神奇,但它非常强大:yield允许我们在生成器函数被next函数调用之间暂停。yield语句是区分生成器函数和普通函数的关键。

实现同一个迭代器的另一种方法是使用生成器表达式。

pythondef square_all(numbers):return (n**2 for n in numbers)

这与我们的生成器函数做同样的事情,但它使用的语法看起来像列表推导式。如果你需要在代码中创建一个惰性可迭代对象,考虑迭代器,并尝试创建生成器函数或生成器表达式。

迭代器如何改进你的代码

一旦你接受了在代码中使用惰性可迭代对象的想法,你会发现有很多可能性去发现或创建辅助函数,帮助你遍历可迭代对象和处理数据。

惰性求值与求和

这是一个求和Django查询集中所有可计费小时数的for循环:

pythonhours_worked = 0for event in events:if event.is_billable():hours_worked += event.duration

下面的代码使用生成器表达式进行惰性求值,做了同样的事情:

pythonbillable_times = (event.durationfor event in eventsif event.is_billable())hours_worked = sum(billable_times)

注意,我们代码的结构发生了巨大变化。

将可计费时间转换为惰性可迭代对象,让我们可以为之前未命名的东西(billable_times)命名。这也让我们能够使用sum函数。我们之前不能使用sum函数,因为我们甚至没有一个可迭代对象可以传入它。迭代器允许你从根本上改变代码的结构。

惰性求值与跳出循环

这段代码打印日志文件的前10行:

pythonfor i, line in enumerate(log_file):if i >= 10:breakprint(line)

这段代码做了同样的事情,但我们使用itertools.islice函数在遍历过程中惰性地获取文件的前10行:

pythonfrom itertools import islicefirst_ten_lines = islice(log_file, 10)for line in first_ten_lines:print(line)

我们创建的first_ten_lines变量是一个迭代器。再次使用迭代器,让我们可以为之前未命名的东西(前10行)命名。命名事物可以使我们的代码更具描述性和可读性。

此外,我们还不需要在循环中使用break语句,因为islice工具会为我们处理跳出逻辑。

你可以在标准库的itertools中,以及第三方库(如boltonsmore-itertools)中找到更多的迭代辅助函数。

创建自己的迭代辅助函数

你可以在标准库和第三方库中找到循环辅助函数,但你也可以创建自己的辅助函数!

这段代码创建了一个列表,包含序列中连续值之间的差值。

pythoncurrent = readings[0]for next_item in readings[1:]:differences.append(next_item - current)current = next_item

注意,这段代码有一个额外的变量,我们需要在每次循环时赋值。还要注意,这段代码只适用于可以切片的东西,比如序列。如果readings是生成器、zip对象或任何其他类型的迭代器,这段代码会失败。

让我们编写一个辅助函数来修复我们的代码。

这是一个生成器函数,它为给定可迭代对象中的每个元素,返回(当前元素,下一个元素)的元组:

pythondef with_next(iterable):"""Yield (current, next_item) tuples for each item in iterable."""iterator = iter(iterable)current = next(iterator)for next_item in iterator:yield current, next_itemcurrent = next_item

我们手动从可迭代对象中获取一个迭代器,调用next函数获取第一个元素,然后遍历迭代器获取所有后续元素,并在过程中跟踪最后一个元素。这个函数不仅适用于序列,还适用于任何类型的可迭代对象。

这是同样的代码,但我们使用辅助函数,而不是手动跟踪next_item

pythondifferences = []for current, next_item in with_next(readings):differences.append(next_item - current)

注意,这段代码没有在循环中出现尴尬的next_item赋值。with_next生成器函数为我们处理了跟踪next_item的工作。

还要注意,这段代码已经足够简洁,我们甚至可以将其改写成列表推导式(如果需要的话)。

pythondifferences = [(next_item - current)for current, next_item in with_next(readings)]

重温循环陷阱

到这里,我们已经准备好回到之前看到的那些奇怪示例,试着弄清楚到底发生了什么。

陷阱1:耗尽迭代器

这里我们有一个生成器对象squares

python>>> numbers = [1, 2, 3, 5, 7]>>> squares = (n**2 for n in numbers)

如果我们将这个生成器传入元组构造函数,我们会得到一个包含其元素的元组:

python>>> numbers = [1, 2, 3, 5, 7]>>> squares = (n**2 for n in numbers)>>> tuple(squares)(1, 4, 9, 25, 49)

如果我们然后尝试计算这个生成器中数字的和,我们会得到0

python>>> sum(squares)0

这个生成器现在是空的:我们已经耗尽了它。如果我们再次尝试将其转换为元组,我们会得到一个空元组:

python>>> tuple(squares)()

生成器是迭代器。而迭代器是一次性的可迭代对象。它们就像无法重新装填的Hello Kitty PEZ糖果盒。

陷阱2:部分消费迭代器

我们再次使用生成器对象squares

python>>> numbers = [1, 2, 3, 5, 7]>>> squares = (n**2 for n in numbers)

如果我们询问9是否在生成器squares中,我们会得到True

python>>> 9 in squaresTrue

但如果我们再次询问同样的问题,我们会得到False

python>>> 9 in squaresFalse

当我们询问9是否在这个生成器中时,Python必须遍历这个生成器来寻找9。如果我们在检查9之后继续遍历它,我们只会得到最后两个数字,因为我们已经消费了在此之前的数字:

python>>> numbers = [1, 2, 3, 5, 7]>>> squares = (n**2 for n in numbers)>>> 9 in squaresTrue>>> list(squares)[25, 49]

询问某个元素是否包含在迭代器中,会部分消费该迭代器。不开始遍历迭代器,就无法知道某个元素是否在其中。

陷阱3:解包就是迭代

当你遍历字典时,你得到的是键:

python>>> counts = {'apples': 2, 'oranges': 1}>>> for key in counts:... print(key)...applesoranges

解包字典时,你得到的也是键:

python>>> x, y = counts>>> x, y('apples', 'oranges')

循环依赖于迭代器协议。可迭代对象解包也依赖于迭代器协议。解包字典实际上和遍历字典是一样的。两者都使用迭代器协议,所以在两种情况下你得到的结果是相同的。

总结与相关资源

序列是可迭代对象,但并非所有可迭代对象都是序列。当有人说可迭代对象时,你只能假设他们指的是可以被迭代的东西。不要假设可迭代对象可以被循环两次、可以获取长度或可以被索引。

迭代器是Python中最基本的可迭代对象形式。如果你想在代码中创建一个惰性可迭代对象,考虑迭代器,并尝试创建生成器函数或生成器表达式。

最后,请记住,Python中的所有迭代类型都依赖于迭代器协议,因此理解迭代器协议是理解Python中循环机制的关键。

最新文章

随机文章

基本 文件 流程 错误 SQL 调试
  1. 请求信息 : 2026-03-27 10:00:09 HTTP/2.0 GET : https://f.mffb.com.cn/a/481792.html
  2. 运行时间 : 0.194385s [ 吞吐率:5.14req/s ] 内存消耗:4,788.13kb 文件加载:140
  3. 缓存信息 : 0 reads,0 writes
  4. 会话信息 : SESSION_ID=37ef5b9daf51620d029c9d6661fc42f2
  1. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/public/index.php ( 0.79 KB )
  2. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/autoload.php ( 0.17 KB )
  3. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/composer/autoload_real.php ( 2.49 KB )
  4. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/composer/platform_check.php ( 0.90 KB )
  5. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/composer/ClassLoader.php ( 14.03 KB )
  6. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/composer/autoload_static.php ( 4.90 KB )
  7. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-helper/src/helper.php ( 8.34 KB )
  8. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-validate/src/helper.php ( 2.19 KB )
  9. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/helper.php ( 1.47 KB )
  10. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/stubs/load_stubs.php ( 0.16 KB )
  11. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Exception.php ( 1.69 KB )
  12. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-container/src/Facade.php ( 2.71 KB )
  13. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/symfony/deprecation-contracts/function.php ( 0.99 KB )
  14. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/symfony/polyfill-mbstring/bootstrap.php ( 8.26 KB )
  15. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/symfony/polyfill-mbstring/bootstrap80.php ( 9.78 KB )
  16. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/symfony/var-dumper/Resources/functions/dump.php ( 1.49 KB )
  17. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-dumper/src/helper.php ( 0.18 KB )
  18. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/symfony/var-dumper/VarDumper.php ( 4.30 KB )
  19. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/App.php ( 15.30 KB )
  20. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-container/src/Container.php ( 15.76 KB )
  21. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/psr/container/src/ContainerInterface.php ( 1.02 KB )
  22. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/app/provider.php ( 0.19 KB )
  23. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Http.php ( 6.04 KB )
  24. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-helper/src/helper/Str.php ( 7.29 KB )
  25. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Env.php ( 4.68 KB )
  26. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/app/common.php ( 0.03 KB )
  27. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/helper.php ( 18.78 KB )
  28. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Config.php ( 5.54 KB )
  29. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/config/app.php ( 0.95 KB )
  30. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/config/cache.php ( 0.78 KB )
  31. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/config/console.php ( 0.23 KB )
  32. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/config/cookie.php ( 0.56 KB )
  33. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/config/database.php ( 2.48 KB )
  34. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/facade/Env.php ( 1.67 KB )
  35. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/config/filesystem.php ( 0.61 KB )
  36. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/config/lang.php ( 0.91 KB )
  37. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/config/log.php ( 1.35 KB )
  38. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/config/middleware.php ( 0.19 KB )
  39. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/config/route.php ( 1.89 KB )
  40. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/config/session.php ( 0.57 KB )
  41. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/config/trace.php ( 0.34 KB )
  42. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/config/view.php ( 0.82 KB )
  43. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/app/event.php ( 0.25 KB )
  44. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Event.php ( 7.67 KB )
  45. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/app/service.php ( 0.13 KB )
  46. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/app/AppService.php ( 0.26 KB )
  47. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Service.php ( 1.64 KB )
  48. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Lang.php ( 7.35 KB )
  49. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/lang/zh-cn.php ( 13.70 KB )
  50. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/initializer/Error.php ( 3.31 KB )
  51. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/initializer/RegisterService.php ( 1.33 KB )
  52. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/services.php ( 0.14 KB )
  53. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/service/PaginatorService.php ( 1.52 KB )
  54. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/service/ValidateService.php ( 0.99 KB )
  55. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/service/ModelService.php ( 2.04 KB )
  56. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-trace/src/Service.php ( 0.77 KB )
  57. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Middleware.php ( 6.72 KB )
  58. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/initializer/BootService.php ( 0.77 KB )
  59. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/Paginator.php ( 11.86 KB )
  60. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-validate/src/Validate.php ( 63.20 KB )
  61. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/Model.php ( 23.55 KB )
  62. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/model/concern/Attribute.php ( 21.05 KB )
  63. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/model/concern/AutoWriteData.php ( 4.21 KB )
  64. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/model/concern/Conversion.php ( 6.44 KB )
  65. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/model/concern/DbConnect.php ( 5.16 KB )
  66. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/model/concern/ModelEvent.php ( 2.33 KB )
  67. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/model/concern/RelationShip.php ( 28.29 KB )
  68. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-helper/src/contract/Arrayable.php ( 0.09 KB )
  69. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-helper/src/contract/Jsonable.php ( 0.13 KB )
  70. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/model/contract/Modelable.php ( 0.09 KB )
  71. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Db.php ( 2.88 KB )
  72. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/DbManager.php ( 8.52 KB )
  73. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Log.php ( 6.28 KB )
  74. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Manager.php ( 3.92 KB )
  75. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/psr/log/src/LoggerTrait.php ( 2.69 KB )
  76. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/psr/log/src/LoggerInterface.php ( 2.71 KB )
  77. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Cache.php ( 4.92 KB )
  78. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/psr/simple-cache/src/CacheInterface.php ( 4.71 KB )
  79. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-helper/src/helper/Arr.php ( 16.63 KB )
  80. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/cache/driver/File.php ( 7.84 KB )
  81. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/cache/Driver.php ( 9.03 KB )
  82. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/contract/CacheHandlerInterface.php ( 1.99 KB )
  83. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/app/Request.php ( 0.09 KB )
  84. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Request.php ( 55.78 KB )
  85. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/app/middleware.php ( 0.25 KB )
  86. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Pipeline.php ( 2.61 KB )
  87. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-trace/src/TraceDebug.php ( 3.40 KB )
  88. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/middleware/SessionInit.php ( 1.94 KB )
  89. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Session.php ( 1.80 KB )
  90. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/session/driver/File.php ( 6.27 KB )
  91. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/contract/SessionHandlerInterface.php ( 0.87 KB )
  92. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/session/Store.php ( 7.12 KB )
  93. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Route.php ( 23.73 KB )
  94. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/route/RuleName.php ( 5.75 KB )
  95. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/route/Domain.php ( 2.53 KB )
  96. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/route/RuleGroup.php ( 22.43 KB )
  97. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/route/Rule.php ( 26.95 KB )
  98. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/route/RuleItem.php ( 9.78 KB )
  99. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/route/app.php ( 1.72 KB )
  100. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/facade/Route.php ( 4.70 KB )
  101. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/route/dispatch/Controller.php ( 4.74 KB )
  102. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/route/Dispatch.php ( 10.44 KB )
  103. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/app/controller/Index.php ( 4.81 KB )
  104. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/app/BaseController.php ( 2.05 KB )
  105. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/facade/Db.php ( 0.93 KB )
  106. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/connector/Mysql.php ( 5.44 KB )
  107. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/PDOConnection.php ( 52.47 KB )
  108. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/Connection.php ( 8.39 KB )
  109. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/ConnectionInterface.php ( 4.57 KB )
  110. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/builder/Mysql.php ( 16.58 KB )
  111. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/Builder.php ( 24.06 KB )
  112. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/BaseBuilder.php ( 27.50 KB )
  113. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/Query.php ( 15.71 KB )
  114. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/BaseQuery.php ( 45.13 KB )
  115. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/concern/TimeFieldQuery.php ( 7.43 KB )
  116. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/concern/AggregateQuery.php ( 3.26 KB )
  117. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/concern/ModelRelationQuery.php ( 20.07 KB )
  118. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/concern/ParamsBind.php ( 3.66 KB )
  119. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/concern/ResultOperation.php ( 7.01 KB )
  120. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/concern/WhereQuery.php ( 19.37 KB )
  121. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/concern/JoinAndViewQuery.php ( 7.11 KB )
  122. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/concern/TableFieldInfo.php ( 2.63 KB )
  123. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-orm/src/db/concern/Transaction.php ( 2.77 KB )
  124. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/log/driver/File.php ( 5.96 KB )
  125. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/contract/LogHandlerInterface.php ( 0.86 KB )
  126. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/log/Channel.php ( 3.89 KB )
  127. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/event/LogRecord.php ( 1.02 KB )
  128. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-helper/src/Collection.php ( 16.47 KB )
  129. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/facade/View.php ( 1.70 KB )
  130. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/View.php ( 4.39 KB )
  131. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Response.php ( 8.81 KB )
  132. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/response/View.php ( 3.29 KB )
  133. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/Cookie.php ( 6.06 KB )
  134. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-view/src/Think.php ( 8.38 KB )
  135. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/framework/src/think/contract/TemplateHandlerInterface.php ( 1.60 KB )
  136. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-template/src/Template.php ( 46.61 KB )
  137. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-template/src/template/driver/File.php ( 2.41 KB )
  138. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-template/src/template/contract/DriverInterface.php ( 0.86 KB )
  139. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/runtime/temp/067d451b9a0c665040f3f1bdd3293d68.php ( 11.98 KB )
  140. /yingpanguazai/ssd/ssd1/www/f.mffb.com.cn/vendor/topthink/think-trace/src/Html.php ( 4.42 KB )
  1. CONNECT:[ UseTime:0.000806s ] mysql:host=127.0.0.1;port=3306;dbname=f_mffb;charset=utf8mb4
  2. SHOW FULL COLUMNS FROM `fenlei` [ RunTime:0.000979s ]
  3. SELECT * FROM `fenlei` WHERE `fid` = 0 [ RunTime:0.000288s ]
  4. SELECT * FROM `fenlei` WHERE `fid` = 63 [ RunTime:0.000252s ]
  5. SHOW FULL COLUMNS FROM `set` [ RunTime:0.000486s ]
  6. SELECT * FROM `set` [ RunTime:0.000207s ]
  7. SHOW FULL COLUMNS FROM `article` [ RunTime:0.000523s ]
  8. SELECT * FROM `article` WHERE `id` = 481792 LIMIT 1 [ RunTime:0.000773s ]
  9. UPDATE `article` SET `lasttime` = 1774576809 WHERE `id` = 481792 [ RunTime:0.002840s ]
  10. SELECT * FROM `fenlei` WHERE `id` = 66 LIMIT 1 [ RunTime:0.000228s ]
  11. SELECT * FROM `article` WHERE `id` < 481792 ORDER BY `id` DESC LIMIT 1 [ RunTime:0.004251s ]
  12. SELECT * FROM `article` WHERE `id` > 481792 ORDER BY `id` ASC LIMIT 1 [ RunTime:0.004676s ]
  13. SELECT * FROM `article` WHERE `id` < 481792 ORDER BY `id` DESC LIMIT 10 [ RunTime:0.002407s ]
  14. SELECT * FROM `article` WHERE `id` < 481792 ORDER BY `id` DESC LIMIT 10,10 [ RunTime:0.006620s ]
  15. SELECT * FROM `article` WHERE `id` < 481792 ORDER BY `id` DESC LIMIT 20,10 [ RunTime:0.010970s ]
0.196017s