
Ich möchte ein Skript schreiben, das meine Eingabe liest (wenn mein Skript beispielsweise „check“ heißt, gebe ich „check 9 4 1993“ ein und diese Eingabe durchläuft den Befehl „cal“ und prüft anhand des Kalenders, ob es sich um ein gültiges Datum handelt oder nicht).
Meine Idee ist, dass, wenn die Eingabe, die durch den Befehl cal geht, einen Fehler ergibt, dies bedeutet, dass es sich nicht um ein gültiges Datum handelt, und umgekehrt, wenn es keinen Fehler gibt, dann ist das Datum gültig. Mir ist klar, dass mit diesem Entwurf etwas ganz und gar nicht stimmt (ich kann nicht herausfinden, wie ich es so hinbekomme, dass meine Eingabe durch den Befehl cal geht), aber ich wäre für einige Vorschläge dankbar. Hier ist jedenfalls der Entwurf:
#!/bin/bash
day=$1; month=$2; year=$3
day=$(echo "$day" | bc)
month=$(echo "$month" | bc)
year=$(echo "$year" | bc)
cal $day $ month $year 2> /dev/null
if [[$? -eq 0 ]]; then
echo "This is a valid date"
else
echo "This is an invalid date"
fi
Antwort1
In einigen Linux-Distributionen, die ich überprüft habe (z. B. Ubuntu 14.04), cal
stammt das Paket von BSD und nicht von GNU Coreutils. Die BSD-Version scheint keine Tage als Parameter zu akzeptieren; nur Monate und Jahre. Die Ubuntu-Version hat zwar eine Option -H YYYY-MM-DD, aber das scheint nicht zu helfen.
Stattdessen würde ich das Dienstprogramm verwenden date
. Unter der Annahme der GNU Coreutils unter Linux würde ich Ihr Skript wohl etwa so umschreiben:
#!/bin/bash
day=$((10#$1))
month=$((10#$2))
year=$((10#$3))
if date -d $year-$month-$day > /dev/null 2>&1; then
# cal $month $year
echo "This is a valid date"
else
echo "This is an invalid date"
fi
Anmerkungen:
- Ich verwende die Shell-eigenearithmetische Erweiterungum die Eingabe zu validieren/führende Nullen zu entfernen, anstatt
bc
für jeden Parameter einen neuen Prozess zu erstellen - ich benutzeGNU-Datumum das Eingabedatum zu analysieren
- Der date-Befehl kann direkt als bedingter Ausdruck verwendet werden
if
.if
funktioniert, indem Prozess-Exit-Codes überprüft werden. Normalerweise werden stattdessen die ausführbaren Dateien[
oder[[
verwendet, aber es gibt keinen Grund, andere Programme zu verwenden, wenn sie mit nützlichen Exit-Codes beendet werden. - Ich bin nicht sicher, ob Sie die
cal
Ausgabe tatsächlich für korrekte Daten wollten oder nicht. Wenn ja, heben Sie einfach die Kommentierung dercal
Zeile auf.
Antwort2
[[
ist eigentlich ein Befehl und wie bei anderen Befehlen benötigen Sie Leerzeichen, um die Argumente zu trennen:
if [[ $? -eq 0 ]]; then
# ...^
Antwort3
$
Zwischen Ihrem Dollar und Ihrer month
Variable befindet sich ein Leerzeichen :
cal $day $ month $year 2> /dev/null
Es sollte sein:
cal $day $month $year 2> /dev/null
Antwort4
Wenn Sie das Datum im Format „%Y-%m-%d“ oder „%m/%d/&Y“ eingeben (z. B. 2020-11-29 oder 11/29/2020), können Sie die Gültigkeit des Datums mit gnu date (gdate) wie folgt überprüfen:
gdate -d "$1" +'%Y-%m-%d' > /dev/null 2>&1 # don't display any output
status=$(echo $?) # get error code
if [[ $status = 1 ]] # if date is invalid
then
{ echo "This date doesn't exist. Enter valid date!"; exit 1; }
else
...
Hoffe, ich habe die Frage richtig beantwortet und das hilft jemandem. Bei mir hat es auf jeden Fall geklappt :)