Я пытаюсь создать простую игру, в которой нужно собрать столько блоков, сколько вы можете за определенное время, скажем, 10 секунд. Как я могу получить секундомер, чтобы начать тикать в начале программы, и когда он достигнет 10 секунд, сделайте что-нибудь (в этом случае выйдите из цикла)?
Секундомер в Python
Ответ 1
import time
now = time.time()
future = now + 10
while time.time() < future:
# do stuff
pass
В качестве альтернативы, если у вас уже есть цикл:
while True:
if time.time() > future:
break
# do other stuff
Этот метод хорошо работает с pygame, так как он требует от вас большого основного цикла.
Ответ 2
Использование time.time()/datetime.datetime.now() будет прерываться, если системное время будет изменено (пользователь изменяет время, он корректируется службами синхронизации времени, такими как NTP или переключение с/на дневное время сбережения!).
time.monotonic() или time.perf_counter(), кажется, правильный путь, однако они доступны только из python 3.3. Другая возможность - использование threading.Timer. Независимо от того, является ли это более надежным, чем time.time(), а друзья зависят от внутренней реализации. Также обратите внимание, что создание нового потока не является полностью бесплатным с точки зрения системных ресурсов, поэтому это может быть плохой выбор в случаях, когда много таймеров нужно запускать параллельно.
Ответ 3
Я использую эту функцию в своих программах python. Вход для функции приведен в качестве примера:
value = time.time()
def stopWatch(value):
'''From seconds to Days;Hours:Minutes;Seconds'''
valueD = (((value/365)/24)/60)
Days = int (valueD)
valueH = (valueD-Days)*365
Hours = int(valueH)
valueM = (valueH - Hours)*24
Minutes = int(valueM)
valueS = (valueM - Minutes)*60
Seconds = int(valueS)
print Days,";",Hours,":",Minutes,";",Seconds
start = time.time() # What in other posts is described is
***your code HERE***
end = time.time()
stopWatch(end-start) #Use then my code
Ответ 4
Объект threading.Timer
(документация) может подсчитать десять секунд, затем установите его, чтобы установить флаг Event, указывающий, что цикл должен выйти.
Документация указывает, что время может быть неточным - вам нужно будет проверить, достаточно ли он достаточно для вашей игры.
Ответ 5
В этом примере цикл запускается каждую секунду в течение десяти секунд:
import datetime, time
then = datetime.datetime.now() + datetime.timedelta(seconds=10)
while then > datetime.datetime.now():
print 'sleeping'
time.sleep(1)
Ответ 6
Для вспомогательного класса StopWatch вот мое решение, которое дает вам точность в выводе, а также доступ к необработанному времени запуска:
class StopWatch:
def __init__(self):
self.start()
def start(self):
self._startTime = time.time()
def getStartTime(self):
return self._startTime
def elapsed(self, prec=3):
prec = 3 if prec is None or not isinstance(prec, (int, long)) else prec
diff= time.time() - self._startTime
return round(diff, prec)
def round(n, p=0):
m = 10 ** p
return math.floor(n * m + 0.5) / m
Ответ 7
Как упражнение для обучения для себя, я создал класс, чтобы иметь возможность создавать несколько экземпляров таймера секундомера, которые могут вам пригодиться (я уверен, что в модулях времени или подобных случаях есть лучшие/более простые версии)
import time as tm
class Watch:
count = 0
description = "Stopwatch class object (default description)"
author = "Author not yet set"
name = "not defined"
instances = []
def __init__(self,name="not defined"):
self.name = name
self.elapsed = 0.
self.mode = 'init'
self.starttime = 0.
self.created = tm.strftime("%Y-%m-%d %H:%M:%S", tm.gmtime())
Watch.count += 1
def __call__(self):
if self.mode == 'running':
return tm.time() - self.starttime
elif self.mode == 'stopped':
return self.elapsed
else:
return 0.
def display(self):
if self.mode == 'running':
self.elapsed = tm.time() - self.starttime
elif self.mode == 'init':
self.elapsed = 0.
elif self.mode == 'stopped':
pass
else:
pass
print "Name: ", self.name
print "Address: ", self
print "Created: ", self.created
print "Start-time: ", self.starttime
print "Mode: ", self.mode
print "Elapsed: ", self.elapsed
print "Description:", self.description
print "Author: ", self.author
def start(self):
if self.mode == 'running':
self.starttime = tm.time()
self.elapsed = tm.time() - self.starttime
elif self.mode == 'init':
self.starttime = tm.time()
self.mode = 'running'
self.elapsed = 0.
elif self.mode == 'stopped':
self.mode = 'running'
#self.elapsed = self.elapsed + tm.time() - self.starttime
self.starttime = tm.time() - self.elapsed
else:
pass
return
def stop(self):
if self.mode == 'running':
self.mode = 'stopped'
self.elapsed = tm.time() - self.starttime
elif self.mode == 'init':
self.mode = 'stopped'
self.elapsed = 0.
elif self.mode == 'stopped':
pass
else:
pass
return self.elapsed
def lap(self):
if self.mode == 'running':
self.elapsed = tm.time() - self.starttime
elif self.mode == 'init':
self.elapsed = 0.
elif self.mode == 'stopped':
pass
else:
pass
return self.elapsed
def reset(self):
self.starttime=0.
self.elapsed=0.
self.mode='init'
return self.elapsed
def WatchList():
return [i for i,j in zip(globals().keys(),globals().values()) if '__main__.Watch instance' in str(j)]
Ответ 8
Это самый короткий путь, который я знаю об этом:
def stopWatch():
import time
a = 0
hours = 0
while a < 1:
for minutes in range(0, 60):
for seconds in range(0, 60):
time.sleep(1)
print(hours,":", minutes,":", seconds)
hours = hours + 1
Ответ 9
Новое в мире питонов!
Мне нужен независимый от системного времени Секундомер, поэтому я перевел свой старый класс С++ на Python:
from ctypes.wintypes import DWORD
import win32api
import datetime
class Stopwatch:
def __init__(self):
self.Restart()
def Restart(self):
self.__ulStartTicks = DWORD(win32api.GetTickCount()).value
def ElapsedMilliSecs(self):
return DWORD(DWORD(win32api.GetTickCount()).value-DWORD(self.__ulStartTicks).value).value
def ElapsedTime(self):
return datetime.timedelta(milliseconds=self.ElapsedMilliSecs())
У этого не было проблемы на 49 дней из-за математики DWORD, но NOTICE, что GetTickCount
имеет гранулярность около 15 миллисекунд, поэтому не используйте этот класс, если вам нужно 1-100 миллисекунд прошедших временных интервалов.
Любые улучшения или отзывы приветствуются!