在编写算法过程中,常常会使用到for循环,而当循环时间过长时我们有期望得到一个定时的进度条,已有的是tqdm包,可以实现进度条,但很多时候并不是我们想要的样子,下面给出一个自定义的类,暂时能满足自己的需求,如果读者有需求可以联系作者,对类进行更新「写的很粗糙很粗糙很粗糙,仅供参考」,暂时有一个bug,即每次循环时间小于1s无法进行剩余时长预测。
class ProcessAndTime():
def __init__(self, l, split=0.1, timemode='a', mode='stp', flash=False):
"""
:param l: 准备进行for循环的序列
:param split: 将序列分割输出进度的比例,如:split=0.1,则程序每进行0.1*数据总数输出一次进度,默认为0.1
:param timemode: 输出时间时设置输出时间格式,'a'代表HMS类型(如:1h12min54s),'s'代表S类型(如:320s),默认为'a'
:param mode: 输出进度的格式,有's','t','p'三种,分别代表'程序运行进度','已经运行时间','预测剩余时间'
可以进行顺序不同的组合(如:'stp'代表输出'程序进行进度:已经运行时间:预测剩余时间:'),默认为'stp'
:param flash: 设置是否刷新控制台,默认为False,设置True后可以刷新输出,此时建议将split设置小点
"""
import datetime
self.sequence = l
self.n = len(l)
self.count = 0
self.begin_time = datetime.datetime.now()
self.time1 = self.begin_time
self.time2 = self.begin_time
self.split = split
self._split = int(split * self.n)
self.timemode = timemode
self.mode = mode
self.flash = flash
def Print(self):
if self.count % self._split == 0:
if self.flash:
print('\r', end='')
self.time2 = datetime.datetime.now()
schedule = self.count / self.n
_t = self.time2 - self.begin_time
_t = _t.seconds
t_ = self.time2 - self.time1
if schedule == 0:
t_ = 0
else:
t_ = int(t_.seconds * (1 / self.split) * (1 - schedule))
_t, t_ = self.seconds2hour(_t), self.seconds2hour(t_)
schedule *= 100
for i in self.mode:
if i == 's':
print("运行进度:{:.2f}% ".format(schedule), end='')
elif i == 't':
print("运行时间:{} ".format(_t), end='')
elif i == 'p':
print("预测剩余时间:{} ".format(t_), end='')
else:
raise Exception('mode仅接受 \'s\', \'p\', \'t\'的组合')
else:
if self.flash:
pass
else:
print()
self.time1 = datetime.datetime.now()
self.count += 1
def seconds2hour(self, t):
if self.timemode == 'a':
if t <= 60:
t = str(t) + 's'
elif 60 <= t <= 3600:
t = str(t // 60) + 'm' + str(t % 60) + 's'
elif t >= 3600:
t = str(t // 3600) + 'h' + str((t % 3600) // 60) + 'm' + str((t % 3600) % 60) + 's'
elif self.timemode == 's':
t = str(t) + 's'
else:
raise Exception('timemode仅接受 \'a\', \'s\'两种')
return t
下面是类使用方法和示例,本类需要定义在for循环前,在for循环内调用print方法使用
import time
l = list(range(100))
t = ProcessAndTime(l)
for i in l:
t.Print()
time.sleep(0.1)
运行进度:0.00% 运行时间:0s 预测剩余时间:0s
运行进度:10.00% 运行时间:1s 预测剩余时间:9s
运行进度:20.00% 运行时间:2s 预测剩余时间:8s
运行进度:30.00% 运行时间:3s 预测剩余时间:7s
运行进度:40.00% 运行时间:4s 预测剩余时间:6s
运行进度:50.00% 运行时间:5s 预测剩余时间:5s
运行进度:60.00% 运行时间:6s 预测剩余时间:4s
运行进度:70.00% 运行时间:7s 预测剩余时间:3s
运行进度:80.00% 运行时间:8s 预测剩余时间:1s
运行进度:90.00% 运行时间:9s 预测剩余时间:0s
import time
l = list(range(100))
t = ProcessAndTime(l, mode='pt', timemode='s')
for i in l:
t.Print()
time.sleep(0.1)
预测剩余时间:0s 运行时间:0s
预测剩余时间:9s 运行时间:1s
预测剩余时间:8s 运行时间:2s
预测剩余时间:7s 运行时间:3s
预测剩余时间:6s 运行时间:4s
预测剩余时间:5s 运行时间:5s
预测剩余时间:4s 运行时间:6s
预测剩余时间:3s 运行时间:7s
预测剩余时间:1s 运行时间:8s
预测剩余时间:0s 运行时间:9s