1Danke
ERLEDIGT
NEIN
NEIN
ANTWORTEN
8
8
ZUGRIFFE
589
589
EMPFEHLEN
-
Hallo PHPler
Ich möchte den relativen Zeitversatz zum heutigen Tag ausgeben. Zum Beispiel: heute, gestern, morgen, am Sonntag, vor 12 Tagen, etc.
Ich habe jetzt schon viele Möglichkeiten versucht. Rechnen mit dem timestamp und den vergangenen Sekunden geht nicht. Ist es aktuell 00:05 Uhr und mein Vergleichszeitpunkt ist 10 Minuten früher, dann will ich "gestern" ausgeben. Also kann ich nicht mit den verstrichenen Sekunden arbeiten.
Mit einem DateTime-Objekt und diff() kann ich scheinbar auch nicht korrekt rechnen. Denn zum einen erhalte ich immer nur positive Werte (egal ob es vor 3 Tagen ist oder in 3 Tagen). Außerdem scheint diff() nicht in Tagen sondern auch in Zeitabständen zu rechnen. Gestern muss also mindestens 24 Stunden zurück liegen. Andernfalls ist es nicht gestern
Ein Zeitpunkt vor 20 Stunden wird leider auch als "heute" ausgegeben.PHP-Code:$today = new DateTime();
$yesterday = new DateTime('-1 day');
$tomorrow = new DateTime('+1 day');
$due = new DateTime($date);
$span = $due->diff($today)->days;
if ($span == 0)
{
return 'heute';
}
Was kann ich bei der Misere mache?
Für heute, morgen, gestern kann ich noch einen direkten Datumsvergleich (Y-m-d) machen. Aber wie berechnen ich die tatsächlichen vergangenen Tage?
Sorry, ich glaube ich habe mich etwas umständlich ausgedrückt
Hoffe dennoch auf Unterstützung. Danke und Grüße.
-
09.12.11 19:39 #2
- Registriert seit
- Oct 2007
- Beiträge
- 31
Also wenn ich dich richtig verstanden habe, willst so etwas wie Zeitzonen simulieren? Du brauchst doch nur von deinem aktuellen Timestamp, den Versatz subtrahieren, schon hast du deine neue Zeit.
PHP-Code:// Dein Timestamp
$timestamp = time();
// Der Versatz
$timeFactor = 60 * 60 * 24;
// Deine Zeit mit Versatz
$localTime = $timstamp - $timeFactor;
// Datumsformat
$timeFormat = DATE_COOKIE; // siehe http://www.php.net/date
// Zeit formatieren und ausgeben
echo date($imeFormat, $localTime);
-
Danke für deine Antwort. Die Zeitzone ist glaube ich bei der relative Zeitausgabe egal.
"Vor 3 Tagen" bleibt "vor 3 Tagen", egal ob in Berlin oder New York.
Mir geht es darum, dass ich nicht in ganzen Tagen rechnen kann.
Angenommen jetzt ist: 2011-12-09 20:00:00
Ich will den relativen Zeitversatz (Differenz in Tagen) zu folgenden Zeitpunkten:
2011-12-08 16:00:00
2011-12-08 22:00:00
2011-12-24 10:00:00
Würde ich jetzt die Differenz in Sekunden berechnen, dann liegt das zweite Datum nur 22 Stunden zurück. Also keinen ganzen Tag in Sekunden ausgedrückt. Dennoch ist es für jeden Mensch "gestern". Es lässt sich jedoch schwer oder nur umständlich berechnen.
Ich denke ich habe eine Lösung gefunden. Ich ziehe die Differenz aus allen Tage zu dem gewünschten Datum um 0 Uhr. Dann gibt es keine Rundungsfehler
Vielleicht hat ja jemand ein besseren Vorschlag.
PHP-Code:function relative_date($date)
{
$due = strtotime($date);
$now = time();
setlocale (LC_ALL, 'de_DE');
$today = date('Y-m-d', $now);
$yesterday = strftime('%Y-%m-%d', strtotime('-1 day', $now));
$tomorrow = strftime('%Y-%m-%d', strtotime('+1 day', $now));
//echo $tomorrow;
// Today at 00:00:00 o'clock
$today_day = strftime('%d', time());
$today_month = strftime('%m', time());
$today_year = strftime('%Y', time());
$pastdays = mktime(0, 0, 0, $today_month, $today_day, $today_year) / 86400;
// The due date at 00:00:00 o'clock
$due_day = strftime('%d', $due);
$due_month = strftime('%m', $due);
$due_year = strftime('%Y', $due);
$newdue = mktime(0, 0, 0, $due_month, $due_day, $due_year);
$daydiff = $pastdays - ($newdue / 86400);
if (strftime('%Y-%m-%d', $due) == $today)
{
return 'heute';
}
if (strftime('%Y-%m-%d', $due) == $yesterday)
{
return 'gestern';
}
if (strftime('%Y-%m-%d', $due) == $tomorrow)
{
return 'morgen';
}
// Due is in the past
if ($due < $now)
{
// Last 7 days
if ($span < 604800)
{
return 'letzter ' . strftime('%A', $due) . ' <span class="light">('. $daydiff .' Tage überfällig)</span>';
}
else
{
return strftime('%d. %b', $due) . ' <span class="light">('. floor($span/86400) .' Tage überfällig)</span>';
}
}
else // Due is in the future
{
$span = $span * -1;
if ($span < 604800)
{
return strftime('%A', $due);
}
else
{
return strftime('%d. %b', $due) . ' <span class="light">(' . strftime('%V', $due) . '. KW, in '. floor($span/86400) .' Tage)</span>';
}
}
return $date;
}
-
10.12.11 10:45 #4
- Registriert seit
- May 2006
- Ort
- There is no place like 127.0.0.1
- Beiträge
- 3.521
Genauso muss man es machen, es gibt keine andere Lösung, vielleicht einen generalisierten Ansatz. Ist die DateTime-Klasse die aus der SPL (also PHP-Standard)? Dann habe ich eine schönere Lösung für dich:
Code php:1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41
<?php ini_set('display_errors', 1); error_reporting(E_ALL|E_STRICT); date_default_timezone_set('Europe/Berlin'); class CustomDateTime extends DateTime { /** * This function calculates the due of days to now from an specific date * * @param DateTime $fromDate The date to calculate the days */ public function dueDays(DateTime $fromDate) { // Get the current time stamp $nowTimestamp = $this->getTimestamp(); // Get the time stamp of the date and time to calculate the due days $fromDateTimestamp = $fromDate->getTimestamp(); // Get the first hour of the date now $todayZero = $nowTimestamp - ($nowTimestamp % 86400); // Get the first hour of the date to calculate the due days $fromDayZero = $fromDateTimestamp - ($fromDateTimestamp % 86400); // Calculate the difference in days $diffDays = ($todayZero - $fromDayZero) / 86400; return abs($diffDays); } } $now = new CustomDateTime(); $yesterday = new CustomDateTime('-1day'); $specificDate = new CustomDateTime('2011-12-06 17:30'); $tomorrow = new CustomDateTime('+1day'); $nextWeek = new CustomDateTime('+1week'); echo $now->dueDays($yesterday) . "<br/><br/>"; echo $now->dueDays($specificDate) . "<br/><br/>"; echo $now->dueDays($tomorrow) . "<br/><br/>"; echo $now->dueDays($nextWeek) . "<br/><br/>";
EDIT: Habe den Code noch mal angepasst, es werden jetzt absolute Werte zurück gegeben, da man sonst bei "tomorrow" eine -1 zurück bekommt.Geändert von saftmeister (10.12.11 um 10:50 Uhr)
Grüße
--
Qualität des Codes wird in WTF's/Min gemessen: Je mehr, desto schlechter der Code ;-)
-
Ich hatte mal ein ähnliches Problem, hab das aber so gelöst, dass ich mit mktime() den Timestamp um 0:00 brerechnet habe und dann geguckt, ob ein timestamp dazwischen liegt. Zum Beispiel so:
Code :1 2 3 4 5 6 7 8
<?php $gestern = (mktime(0,0,0,date("m",time()),date("d",time()),date("Y",time())) - 86400); $heute = mktime(0,0,0,date("m",time()),date("d",time()),date("Y",time())); if ($timestamp > $gestern AND $timestamp < $heute) echo "Gestern"; ?>
Ist zwar recht umständlich, aber übersichtilich wie ich finde.
-
Danke euch beiden für die Antworten.
Die CustomDateTime-Klasse sieht gut aus. Etwas übersichtlicher als mein Konstrukt
Werde das wohl etwas angepasst übernehmen. Danke dafür!
@kourty
Dein Ansatz ist etwas ähnlich zu meinem. Übersichtlich ist es
Auch dir besten Dank für den Code!
Grüße
suntrop
-
14.12.11 00:10 #7
- Registriert seit
- May 2006
- Ort
- There is no place like 127.0.0.1
- Beiträge
- 3.521
Wenn du eine zusätzliche Methode implementierst, kannst du auch prüfen, ob ein Datum älter ist als das andere:
Code php:1 2 3 4 5 6 7 8 9 10
/** * Checks whether the current date is earlier than the given date as parameter * * @param DateTime $checkDate The date to check against the current * @return boolean true if the current date is earlier, false if not */ public function isEarlierThan(DateTime $checkDate) { return ($this->getTimestamp() < $checkDate->getTimestamp()) ? true : false; }
Im Anhang findest du die CustomDateTime-Klasse mit PHPUnit-Test.Grüße
--
Qualität des Codes wird in WTF's/Min gemessen: Je mehr, desto schlechter der Code ;-)
-
Hallo,
so würde es auch funktionieren:
PHP-Code:<?php
$timeStamp = strtotime('2011-12-24 10:00:00');
$span = unixtojd($timeStamp) - unixtojd();
switch ($span) {
case -1:
$msg = 'gestern';
break;
case 0:
$msg = 'heute';
break;
case 1:
$msg = 'morgen';
break;
case ($span < -1):
$msg = 'vor '.$span*(-1).' Tagen';
break;
default:
$msg = 'in '.$span.' Tagen';
}
echo $msg;
?>
-
Viele Wege führen nach Rom

Die Funktion unixtojd() kannte ich nicht, aber damit ist es ja wirklich simpel eine Tagesdifferenz zu berechnen. Danke für den Tipp!
Ähnliche Themen
-
Automatisches Update nach X Tagen
Von Brölio im Forum PHPAntworten: 4Letzter Beitrag: 15.02.08, 16:50 -
Einträge nach 30 Tagen löschen
Von funnyzocker im Forum Relationale DatenbanksystemeAntworten: 3Letzter Beitrag: 07.04.07, 17:27 -
Einträge nach 30 Tagen löschen
Von funnyzocker im Forum PHPAntworten: 3Letzter Beitrag: 07.04.07, 17:27 -
Outlook-Kalender-Einträge nach X-Tagen verschieben
Von Hawkster im Forum Office-AnwendungenAntworten: 1Letzter Beitrag: 08.09.06, 08:21 -
Tebelle automatisch nach X Tagen löschen
Von Blattspinat im Forum Relationale DatenbanksystemeAntworten: 3Letzter Beitrag: 22.11.04, 22:12





Zitieren

Login






[PHP][Snippet] Array zu XML konvertieren