2009-09-05 13 views

risposta

90

Non riesco a credere che nessuna delle tante risposte dia quello che considererei "l'unico modo ovvio per farlo" (e non sono nemmeno olandese ...! -) - fino a poco meno di 24 vale la pena ore di secondi (86399 secondi, in particolare):

>>> import time 
>>> time.strftime('%H:%M:%S', time.gmtime(12345)) 
'03:25:45' 

Farlo in un modello di Django più schizzinoso, dal momento che il filtro time supporta una sintassi tempo di formattazione funky (ispirato, credo, da PHP), e ha anche bisogno del modulo datetime e dell'implementazione del fuso orario come pytz per preparare i dati.Per esempio:

>>> from django import template as tt 
>>> import pytz 
>>> import datetime 
>>> tt.Template('{{ x|time:"H:i:s" }}').render(
...  tt.Context({'x': datetime.datetime.fromtimestamp(12345, pytz.utc)})) 
u'03:25:45' 

A seconda delle vostre esigenze, potrebbe essere più conveniente per definire un filtro personalizzato per questo compito formattazione nella tua app.

+0

mentre si tratta di un problema minore, che è probabilmente irrilevante per l'OP 'time.strftime ('% H:% M:% S', time.gmtime (864001)) restituisce una brutta sorpresa. – SilentGhost

+1

Sì, funziona solo per un giorno - come la tua soluzione, naturalmente, che si interrompe in modo diverso invece di "avvolgere", dal momento che 'str (datetime.timedelta (seconds = 86400))' dice "1 giorno";) –

+0

:) Non penso che la mia soluzione * si guasta *, fornisce comunque l'output più leggibile, dal momento che OP non ha partecipato alla discussione qui intorno, sono libero di supporre che sia esattamente ciò che vuole . – SilentGhost

8

Hai letto sul modulo di datetime?

Modifica/aggiornamento: La risposta di SilentGhost ha i dettagli che la mia risposta lascia fuori. Se ti piace questa risposta, fai +1 anche a lui (o meglio). Ripubblicato qui:

>>> a = datetime.timedelta(seconds=65) 
datetime.timedelta(0, 65) 
>>> str(a) 
'0:01:05' 
+0

@sth: SilentGhost ha le deets. –

+0

Non credo che nulla in datetime faccia ciò che vuole. Non c'è niente come timedelta.strftime, quindi anche se memorizza il suo "numero di secondi" come timedelta (che probabilmente dovrebbe), dovrebbe comunque eseguire la formattazione da solo. Convertirlo in un tempo sarebbe un hack, dal momento che sembra avere una quantità di tempo (timedelta) e non un momento della giornata (tempo). –

+0

@Glenn: Cosa c'è che non va nella rappresentazione str()? –

0

Oltre al fatto che Python ha un supporto incorporato per date e orari (vedi la risposta di bigmattyh), trovando minuti o ore da secondi è facile:

minutes = seconds/60 
hours = minutes/60 

Ora, quando si desidera per visualizzare minuti o secondi, MOD loro da 60 in modo che essi non saranno più grandi di 59

+1

minuti è il modulo 60, quindi è sempre <60, quindi ore == 0 ... –

+0

Oops, scusa, intendevo fare quel passo dopo ... risolverà –

0

non essendo una persona di pitone, ma più semplice senza librerie solo:

total = 3800 
seconds = total % 60 
total = total - seconds 
hours = total/3600 
total = total - (hours * 3600) 
mins = total/60 

codice aggiornato, grazie sth

+1

Questo dà 200 ore per 3800 secondi ... – sth

+0

grazie sth , non inserire codice non testato quando sei stanco è stato notato :) – gaqzi

+0

Siamo stati tutti lì ... –

7

È possibile calcolare il numero di minuti e ore dal numero di secondi dalla semplice divisione:

seconds = 12345 
minutes = seconds // 60 
hours = minutes // 60 

print "%02d:%02d:%02d" % (hours, minutes % 60, seconds % 60) 
print "%02d:%02d" % (minutes, seconds % 60) 

Qui // è la divisione pitoni intero.

+1

Per caso, usa divmod. –

1

Basta fare attenzione quando si divide per 60: la divisione tra interi restituisce un numero intero -> 12/60 = 0 a meno che non si importi la divisione dal futuro. Il seguente è copiare e incollato da Python 2.6.2:

IDLE 2.6.2  
>>> 12/60 
0 
>>> from __future__ import division 
>>> 12/60 
0.20000000000000001 
51
>>> a = datetime.timedelta(seconds=65) 
datetime.timedelta(0, 65) 
>>> str(a) 
'0:01:05' 
+0

h: mm: sss non è hh: mm: ss. –

+4

sul serio? e vale la pena di downvote? – SilentGhost

+2

@Glenn: È abbastanza buono ... e se l'OP vuole formattare ulteriormente, non è esattamente la scienza missilistica da qui. –

17

codice che fa quello che è stato richiesto, con esempi, e mostrando come i casi egli non ha specificato sono gestiti:

def format_seconds_to_hhmmss(seconds): 
    hours = seconds // (60*60) 
    seconds %= (60*60) 
    minutes = seconds // 60 
    seconds %= 60 
    return "%02i:%02i:%02i" % (hours, minutes, seconds) 

def format_seconds_to_mmss(seconds): 
    minutes = seconds // 60 
    seconds %= 60 
    return "%02i:%02i" % (minutes, seconds) 

minutes = 60 
hours = 60*60 
assert format_seconds_to_mmss(7*minutes + 30) == "07:30" 
assert format_seconds_to_mmss(15*minutes + 30) == "15:30" 
assert format_seconds_to_mmss(1000*minutes + 30) == "1000:30" 

assert format_seconds_to_hhmmss(2*hours + 15*minutes + 30) == "02:15:30" 
assert format_seconds_to_hhmmss(11*hours + 15*minutes + 30) == "11:15:30" 
assert format_seconds_to_hhmmss(99*hours + 15*minutes + 30) == "99:15:30" 
assert format_seconds_to_hhmmss(500*hours + 15*minutes + 30) == "500:15:30" 

È possibile - e probabilmente dovrebbe - archiviarlo come timedelta anziché come int, ma si tratta di un problema separato e timedelta non rende effettivamente più semplice questa particolare attività.

+0

Votare una soluzione chiara e chiara che fornisce esattamente ciò che è stato richiesto, completo di test - un esempio brillante del sistema di voto di StackOverflow. Qualcuno ha voglia di foggiare? –

+0

+1: risposta piacevole, completa e flessibile; e in parte per contrastare il downvote. (Anche se non ho intenzione di valutare il dibattito di datetime vs questo - presumo che l'OP dirà quello che sperava abbastanza presto.) – tom10

+0

Un dibattito più acceso di quello che stavo cercando, personalmente, per un domanda di base; ci sono cose migliori su cui investire energia ... –

7

Se si utilizza divmod, siete immuni a diversi gusti di divisione intera:

# show time strings for 3800 seconds 

# easy way to get mm:ss 
print "%02d:%02d" % divmod(3800, 60) 

# easy way to get hh:mm:ss 
print "%02d:%02d:%02d" % \ 
    reduce(lambda ll,b : divmod(ll[0],b) + ll[1:], 
     [(3800,),60,60]) 


# function to convert floating point number of seconds to 
# hh:mm:ss.sss 
def secondsToStr(t): 
    return "%02d:%02d:%02d.%03d" % \ 
     reduce(lambda ll,b : divmod(ll[0],b) + ll[1:], 
      [(t*1000,),1000,60,60]) 

print secondsToStr(3800.123) 

Prints:

63:20 
01:03:20 
01:03:20.123 
0

Se avete bisogno di fare questo un sacco, è possibile precalculate tutte le possibili stringhe per numero di secondi in un giorno:

try: 
    from itertools import product 
except ImportError: 
    def product(*seqs): 
     if len(seqs) == 2: 
      for s1 in seqs[0]: 
       for s2 in seqs[1]: 
        yield (s1,s2) 
     else: 
      for s in seqs[0]: 
       for p in product(*seqs[1:]): 
        yield (s,) + p 

hhmmss = {} 
i = 0 
for (h,m,s) in product(range(24),range(60),range(60)): 
    hhmmss[i] = "%02d:%02d:%02d" % (h,m,s) 
    i += 1 

Ora conversione di secondi per formattare strin g è una ricerca veloce dict:

print hhmmss[12345] 

stampe

'03:25:45' 
Problemi correlati