Datumsrechner

Wenn du dir nicht sicher bist, in welchem der anderen Foren du die Frage stellen sollst, dann bist du hier im Forum für allgemeine Fragen sicher richtig.
Antworten
ASCII158
User
Beiträge: 80
Registriert: Samstag 28. September 2002, 15:40
Wohnort: München

Montag 2. Juni 2003, 18:09

Hallo Leute,

ich suche nach einer Funktion, die mir nach Eingabe zweier Daten (z.B. 4.5.2002 17:45 und 2.6.2003 19:07) Die Differenz ausgibt (in diesem Fall
29.0.1. 1:22) Gibt es da was fertiges oder hat einer von euch schonmal sowas gemacht?

Wenn nicht muss ich das wohl selber machen... ;-)
mfg,

10011110
Milan
User
Beiträge: 1078
Registriert: Mittwoch 16. Oktober 2002, 20:52

Montag 2. Juni 2003, 19:58

hmm... Frage: ist es sinnvoll eine Datumsdifferenz mit Monaten anzugeben? Eher doch mit Tagen und Jahren. Das ließe sich dann auch relativ leicht selber machen. Zuerst die Differenz der Tage ausrechnen, dann die Zeitdifferenz (hh:mm:ss). Wenn die Negativ ist, ziehst du einfach nen tag ab und rechnest die negative in normale Zeit um (lässt sich ja leicht machen, wenn man vor dem ausrechnen der Differenz in sekunden umrechnet). Das mit dem Differenzen der Tage rechnest du dann einfach grob in Monate und Jahre auf, oder lässt es.

Nen Codeschnippel für die Tagedifferenzen hab ich noch, als wir vor einiger Zeit in der Schule der Gregorianischen Kalendar hatten... ist ein wenig lang, funktioniert aber ;)

Code: Alles auswählen

def schaltjahr (jahr):
    if (jahr % 400 == 0) or ((jahr % 4 == 0) and (jahr % 100 != 0)) :
        return 1
    else:
        return 0
def tagemonat(jahr,monat):
    if monat == 2:
        return schaltjahr(jahr) + 28
    elif (monat == 4) or (monat == 6) or (monat == 9) or (monat == 11):
        return 30
    else:
        return 31
def davor (j1,m1,t1,j2,m2,t2):
    if j1 < j2:
        return 1
    elif j1 > j2:
        return 0
    elif m1 < m2:
        return 1
    elif m1 > m2:
        return 0
    elif t1 < t2:
        return 1
    else:
        return 0
def nachfolger(jahr,monat,tag):
    j = jahr; m = monat; t = tag
    t = t + 1
    if (t > tagemonat(jahr,monat)):
        t = 1
        m = m + 1
    if (m > 12):
        m = 1
        j = j + 1
    return j,m,t

def tagedifferenz(j1,m1,t1,j2,m2,t2):
    if not davor(j1,m1,t1,j2,m2,t2):
        (j1,m1,t1,j2,m2,t2)=(j2,m2,t2,j1,m1,t1)
    diff=0L
    while davor(j1,m1,t1,j2,m2,t2):
        (j1,m1,t1)=nachfolger(j1,m1,t1)
        diff=diff+1L
    return diff

print tagedifferenz(2003,5,31,2003,6,2)
rAiNm4n

Dienstag 3. Juni 2003, 20:34

wieso benutzt du nicht einfach das Modul time?
konkret würde das dann ungefähr so aussehen:

Code: Alles auswählen

import time
date1 = time.mktime((2002, 5, 4, 17, 45, 0, 0, 0, 0))
date2 = time.mktime((2003, 6, 2, 19, 7, 0, 0, 0, 0))
erg = time.strftime("%d.%m.%Y %H:%M", time.gmtime(date2 - date1))
>>> print erg
'30.01.1971 01:22' (Die Jahreszahl ist hier eher uninterressant...)

Ich hoffe ich konnte dir helfen...
cu

Chris
Milan
User
Beiträge: 1078
Registriert: Mittwoch 16. Oktober 2002, 20:52

Dienstag 3. Juni 2003, 21:01

weil die Monats- und Tageszahl wohl in den seltensten Fällen stimmen dürfte. schließlich wird immer von 1.1.1970 ausgegangen. wenn du eine Differenz bildest, wird angenommen, du würdest einen Zeitpunkt beschreiben, der damals war. Auch dürften die Schaltjahre, die eventuell dazwischen zu beachten sind, rausfallen. Probiers einfach mal mit meinen Angaben ;)

und: man füttert mktime nur mit localtimes und für das zurückrechnen nimmt man dann auch localtime... hab ich Erfahrungen mit gemacht und mich gewundert, warum ich 2 Studen Zeitunterschied hatte...
rAiNm4n

Mittwoch 4. Juni 2003, 11:26

Die Tagesdifferenz, die dein Skript liefert, kannst du aber trotzdem mit dem time-Modul rausbekommen:

Code: Alles auswählen

import time
secs1 = time.mktime((2002, 5, 4, 17, 45, 0, 0, 0, 0))
secs2 = time.mktime((2003, 6, 2, 19, 7, 0, 0, 0, 0))
diff = secs2 - secs1
days = diff / 86400    # diff / 60 / 60 / 24
>>> print days
394.05694444444447
Liefert das selbe Ergebnis, wie dein Skript.

cu
Chris
ASCII158
User
Beiträge: 80
Registriert: Samstag 28. September 2002, 15:40
Wohnort: München

Mittwoch 4. Juni 2003, 17:27

Ich hab mir selber nochn paar Gedanken gemacht:

Code: Alles auswählen

def zeitdifferenz(eins, zwei):
	import calendar
	jahr1, monat1, tag1, stunde1, minute1= eins
	jahr2, monat2, tag2, stunde2, minute2= zwei
	
	for jahr in range(jahr1):
		minute1+=525600+1440*calendar.isleap(jahr)
	
	for monat in range(1,monat1):
		gesamt=calendar.monthcalendar(jahr1, monat)
		tagzahl=0
		for woche in gesamt:
			for tag in woche:
				if tag != 0: tagzahl+=1
		
		minute1+=tagzahl*1440
		
	for tag in range(tag1):
		minute1+=1440
		
	for stunde in range(stunde1):
		minute1+=60
	
	for jahr in range(jahr2):
		minute2+=525600+1440*calendar.isleap(jahr)
	
	for monat in range(1,monat2):
		gesamt=calendar.monthcalendar(jahr2, monat)
		tagzahl=0
		for woche in gesamt:
			for tag in woche:
				if tag != 0: tagzahl+=1
		
		minute2+=tagzahl*1440
		
	for tag in range(tag2):
		minute2+=1440
		
	for stunde in range(stunde2):
		minute2+=60
		
	diff= abs(minute1 - minute2)
	
	jahrn=diff//525600
  	diff -= jahrn*525600
	monatn=diff//43200
	diff -= monatn*43200
	tagn=diff//1440
	diff -= tagn*1440
	stunden=diff//60
	diff -= stunden*60
	minuten=diff
		
	
	return (jahrn, monatn, tagn, stunden, minuten)
	
if __name__=='__main__':
	import time
	print (1986,1,22,16,30)
	print time.gmtime()[:5]
	print zeitdifferenz((1986,1,22,16,30),time.localtime()[:5])
Gibt korrekt:
(1986, 1, 22, 16, 3
(2003, 6, 4, 16, 49
(0, 7, 21, 21, 41)
[/quote][/code]
mfg,

10011110
rAiNm4n
User
Beiträge: 19
Registriert: Mittwoch 4. Juni 2003, 11:30
Wohnort: Berlin

Mittwoch 4. Juni 2003, 19:51

Eine Frage:
Wieso beträgt bei deinem Beispiel die Zeitdifferenz zwischen 22.1.1986 16:30 und 4.6.2003 16:49 nur 7 Monate, 21 Tage, 21 Stunden und 21 Minuten? Also entweder hast du nen Fehler gemacht oder ich blick da nich durch... :roll:
cu

Chris
ASCII158
User
Beiträge: 80
Registriert: Samstag 28. September 2002, 15:40
Wohnort: München

Donnerstag 5. Juni 2003, 13:32

Äh, das weiss ich jatzt auch nicht wie mir das passiert ist, die Ausgabe ist:
(1986, 1, 22, 16, 30)
(2003, 6, 5, 12, 32)
(17, 4, 17, 22, 2)
mfg,

10011110
Voges
User
Beiträge: 564
Registriert: Dienstag 6. August 2002, 14:52
Wohnort: Region Hannover

Donnerstag 5. Juni 2003, 14:54

ASCII158 hat geschrieben:
(1986, 1, 22, 16, 30)
(2003, 6, 5, 12, 32)
(17, 4, 17, 22, 2)
Ich komme händisch auf (17, 4, 13, 20, 2)

Code: Alles auswählen

30 + 2             -> 32      kein Übertrag
16Uhr + 20 Std     -> 12Uhr   nächster Tag   Übertrag!
22. Jan  + 13 Tage -> 6. eines folgenden Monats            
Die 13 setzt sich zusammen aus:
       22. Jan (ausschließlich) bis 31 Jan. sind   9 Tage
       1. Juni bis 5. Juni sind                    5 Tage
       wegen Start am Nachmittag und Ende Mittags -1 Tage
       Summe                                      13 Tage
Jan
Voges
User
Beiträge: 564
Registriert: Dienstag 6. August 2002, 14:52
Wohnort: Region Hannover

Donnerstag 5. Juni 2003, 16:21

Hallo nochmal!
Ich werf' mal mein Skript in die Runde

Code: Alles auswählen

from calendar import monthrange

def datediff(von,bis):
    (jVon,mVon,tVon,stdVon,minVon) = [int(i) for i in von.split()]
    (jBis,mBis,tBis,stdBis,minBis) = [int(i) for i in bis.split()]

    minVon += stdVon*60
    minBis += stdBis*60

    anzMin = minBis - minVon
    if minVon > minBis:
        anzMin += 1440
        tBis -= 1

    anzStd = anzMin // 60
    anzMin = anzMin % 60

    if tVon > tBis:
        anzTage = monthrange(jVon,mVon)[1] - tVon
        anzTage += tBis
    else:
        anzTage = (tBis - tVon)
    
    anzMonate = 0
    if tVon > tBis:
        anzMonate -= 1
    
    anzJahre = jBis - jVon
    if mVon > mBis+anzMonate:
        anzJahre -= 1
        anzMonate += 12 - mVon + mBis
    else:
        anzMonate += mBis - mVon

    return "%d %d %d  %d %d" % (anzJahre,anzMonate,anzTage,anzStd,anzMin)

print datediff("2002 1 5    0 00","2003 1 4   0 00")
print datediff("2002 2 5    0 00","2003 2 4   0 00")
print datediff("2002 12 31 23 00","2003 1 1   1 00")
print datediff("2004 4 4    4 44","2005 4 4   4 43")
print datediff("1986 1 22  16 30","2003 6 5  12 32")
Ausgabe:
0 11 30 0 0
0 11 27 0 0
0 0 0 2 0
0 11 29 23 59
17 4 13 20 2

Sehr sinnvoll erscheint mir die gleichzeitige Angabe von Monaten und Tagen als Differenzen aber wirklich nicht (siehe die ersten beiden Beispiele).
Jan
Antworten