RegEx für strtotime()

Moin again.

Ich brauche einen RegEx für strtotime.

Und zwar ahbe ich ein Textfeld, in das ein Datum im Deutschen oder Amerikanischen Format, mit oder ohne Uhrzeit. Ich will nun mittelspreg_match herauskriegen, ob deutsch, amerikanisch oder gar kein Datum, und mittels preg_replace gegebenfalls den String so umwandeln, das er parsebar wird.

Hier mein Ansatz(erstmal nur für deutsch -> amerikanisch, der preg_matsch kommt in vereinfachter form mit einem if davor.):

preg_replace("#(\d{2})\.(\d{2})\.(\d{4}) ?((\d{2}\:\d{2})(\:\d{2})?)?#i", "$3-$2-$1" . ((empty("$5"))? "00:00" : "$5") . ((empty("$6"))? ":00" : "$6") , $_POST['datum']);

Allerdings gibt mir das:

-> Der Fehler matscht die Zeile mit diesem preg_replace, durch Auskommentieren weiss ich, das es am 2 Parameter liegt.

Ich habe da jetzt eine Weile dran rumgeschraubt, und alles mögliche ausprobiert, aber iwie passt es nie, oder es funzt nicht.
Wenn ihr mir helfen könnt, wäre ich euch dankbar wenn ihr euren Lösungsweg kurz beschreiben könnt, da ich das erste mal mit RegEx-Replace, und auch kaum mit RegEx arbeite.

Greez:

jw-lighting

Du kannst keine Funktion wie empty auf die Back-References wie $5 anwenden - weil es die noch gar nicht gibt zu dem Zeitpunkt, wo dieser Ausdruck ausgewertet wird; das passiert naemlich noch bevor preg_replace ueberhaupt an zu suchen faengt.

Ausserdem nimmt empty ausschliesslich Variablen als Parameter - du versuchst aber, ein Textliteral zu uebergeben.

Gut, wie lässt sich das, was ich dort versuche mit den ifs, denn auswerten?
kann man vllt irgendiwe ne Funktion dafür schreiben oder so?
Und ist mein RegEx so richtig?

Mit „ifs“ an einer Stelle, wo diese zum richtigen Zeitpunkt ausgefuehrt werden.

und wo ist das? gibt es (wieich schon fragte), evtl. die möglichkeit dafür ne funktion zu schreiben, die das dann übernimmt?

Zum Beispiel nach dem RegEx.

Hilft mir immer noch nicht… soll ich jetzt die sachen in nen csv packen, hinterher wieder auseinaderpflücken und verarbeiten? stell ich mir nicht besonders effektiv vor^^.

Sorry, ich hab bisher nur wenig Ahnung über RegEx, was auch daran liegt, das ich bisher kein Buch kenne, das das leicht Verständlich und gut erklärt!
Wenn du so ganau werden könntest, das auch ich als Neuling auf dem Gebiet RegEx verstehe, was du meinst, wäre echt Klasse. :sweat: :uhoh:

“Some people, when confronted with a problem, think ‘I know, I’ll use regular expressions.’ Now they have two problems.” - Jamie Zawinski

Regulaere Ausdruecke haben genau einen Einsatzzweck: Mustersuche.
Sie fuer etwas anderes gebrauchen zu wollen, ist ein Missbrauch.

Die Frage, “gibt es in diesem Text etwas, dass aus zwei Ziffern, gefolgt von einem Punkt, gefolgt von zwei Ziffern, gefolgt von … besteht” - ja, das ist eine Mustersuche.

Die Entscheidung, wenn in dem, was ich fuer eine Datumsangabe halte, keine Uhrzeit angegeben ist, dann moechte ich stattdessen “00:00” verwenden - das ist eine Frage der Programmlogik.

Also splitte deine Datumsangabe in ihre einzelnen Bestandteile auf - und schaue dir anschliessend diese Bestandteile an, und ersetze ihren Inhalt ggf. durch etwas anderes, wenn er dir nicht gefaellt.

Wofuer du allerdings eine nicht vorhandene Uhrzeitangabe ueberhaupt ersetzen moechtest, verstehe ich in diesem Zusammenhang auch nicht - strtotime ist es egal, ob du ein Datum ohne Uhrzeitangabe, oder ein Datum mit dahinterhaengendem “00:00:00” als Parameter verwendest - das Ergebnis ist das gleiche.

Em ja, den kenn ich. Sag mir wies bessere geht :wink:
EDIT: Oder ist das, was ich unten gepostet habe eine gute Lösung?

Puhh… :hail:

:wink:

OK, und wie trenne ich das am besten? Doch nicht etwa, in dem ich mir die einzelnen Informationen da raus fische, in ein CSV packe, und hinterher die CSV wieder auseinader fische, und dann weiterarbeite :whata:
Help please :wink: :sweat:

Du meinst ich soll erst mit String-Funktionen in Tag, Monat, Jahr etc. aufteilen, die dann mit preg_match untersuchen und dann ggf. ersetzen? (*)

[quote=„chrisb“]
Wofuer du allerdings eine nicht vorhandene Uhrzeitangabe ueberhaupt ersetzen moechtest, verstehe ich in diesem Zusammenhang auch nicht - strtotime ist es egal, ob du ein Datum ohne Uhrzeitangabe, oder ein Datum mit dahinterhaengendem „00:00:00“ als Parameter verwendest - das Ergebnis ist das gleiche.[/quote]

Danke, daran hatte ich nicht gedacht. Geht es auch, das ich die Uhrzeit ohne Sekunden übergebe?

Wäre dann das hier schon ausreichend, um aus einem deutschen Datum ein amerikanisches Zu machen? Oder funzt das nicht?
ODER ist die Lösung mit den Strinfunktionen(-> *) oben besser ?

preg_replace("#(\d{2})\.(\d{2})\.(\d{4}) ?((\d{2}\:\d{2})(\:\d{2})?)?#i", "$3-$2-$1 $5"."$6" , $_POST['name']);

Wieso denn CSV bitte?

Es gibt auch noch andere preg-Funktionen.

War ein Beispiel, weils mir grad am schnellsten einfiel :wink:

[quote=„chrisb“]

Es gibt auch noch andere preg-Funktionen.[/quote]

Ja, klar. Und wie siehts mit der von mir geposteten Lösung mit preg_replace aus?

EDIT:

Schneint zu funzen, aber sicher ist das noch nicht wirklich, schliesslich kann man auch noch
39.19.7899 29:69:69 eingeben, selbst wenn ich das so abänder:

preg_replace("#([0-3]\d)\.([0-1]\d)\.(\d{4}) ?(([0-2]\d\:[0-5]\d)(\:[0-5]\d)?)?#i", "$3-$2-$1 $5"."$6" , $_POST['name']);

keine anwort mehr… :astonished:

ich habs jetzt so:

if (preg_match("#[0-3]\d\.[0-1]\d\.\d{4} ?(([0-2]\d\:[0-5]\d)(\:[0-5]\d)?)?#i", $_POST['name']))
echo preg_replace("#([0-3]\d)\.([0-1]\d)\.(\d{4}) ?(([0-2]\d\:[0-5]\d)(\:[0-5]\d)?)?#i", "$3-$2-$1 $5"."$6" , $_POST['name']);
else if(preg_match("#\d{4}\-[0-1]\d\-[0-3]\d ?(([0-2]\d\:[0-5]\d)(\:[0-5]\d)?)?#i", $_POST['name']))
echo preg_replace("#(\d{4})\-([0-1]\d)\-([0-3]\d) ?(([0-2]\d\:[0-5]\d)(\:[0-5]\d)?)?#i", "$1-$2-$3 $5"."$6" , $_POST['name']);
else
echo "Datum nicht Parsebar.";

Das scheint soweit zu funktionieren.
Muss ich noch irgendwas beachten, bevor ich das auf strtotime loslasse, oder geht das schon so?

Habs jetzt, funzt auch soweit:

if (preg_match("#^[0-3]\d\.[0-1]\d\.\d{4} ?(([0-2]\d\:[0-5]\d)(\:[0-5]\d)?)?$#i", $_POST['date']))
$datumstr = preg_replace("#([0-3]\d)\.([0-1]\d)\.(\d{4}) ?(([0-2]\d\:[0-5]\d)(\:[0-5]\d)?)?#i", "$3-$2-$1 $5"."$6" , $_POST['date']);
else if(preg_match("#^\d{4}\-[0-1]\d\-[0-3]\d ?(([0-2]\d\:[0-5]\d)(\:[0-5]\d)?)?$#i", $_POST['date']))
$datumstr = preg_replace("#(\d{4})\-([0-1]\d)\-([0-3]\d) ?(([0-2]\d\:[0-5]\d)(\:[0-5]\d)?)?#i", "$1-$2-$3 $5"."$6" , $_POST['date']);
else
$datum = false;

ähhm…

setlocale("DE_at");
$date = strtotime("28.08.1992 20:00");

echo date("m.d.y H:i", $date);

gibt 28.08.92 20:00 aus…

[quote=“michi7x7”]ähhm…

setlocale("DE_at");
$date = strtotime("28.08.1992 20:00");

echo date("m.d.y H:i", $date);

gibt 28.08.92 20:00 aus…[/quote]
Weiss nicht, wo du das getestet hast - aber hier auf bplaced bekomme ich 08.28.92 20:00 heraus.

(Und der setlocale-Aufruf bleibt natuerlich wirkungslos, wenn du ihm zu wenige Parameter mitgibst.)

na gut, das wäre natürlich auch eine Möglichkeit gewesen… :wink:
Was ist den schneller und sicherer?

ähmm… ja soll es auch ausgeben (m.d.y). Richtig ist natürlich d.m.y

@setlocale: Das war aus dem Kopf, der blöderweise nicht mehr ganz nüchtern war :ps:

setlocale(LC_ALL, 'de_AT');
$date = strtotime("28.08.1992 20:00");

echo date("d.m.Y H:i", $date);

und? ist das schneller?
und wenn ich jetzt ein amerikanisches datum einlese?

setlocale(LC_ALL, 'de_AT');
$date = strtotime("1992-08-28 20:00");

echo date("d.m.Y H:i", $date);

gibt auch 28.08.1992 20:00 aus…