SPRINTF w skryptach shell?
Mam automatycznie generowany plik każdego dnia, który jest wywoływany przez skrypt powłoki. Ale problem, z którym się borykam, polega na tym, że automatycznie wygenerowany plik ma postać:
FILE_MM_DD.dat
... gdzie MM i DD są ciągami dwucyfrowymi miesiąca i dnia miesiąca.
Poszperałem trochę i sam to zrobiłem, ale nie wiem, jak stworzyć te niestandardowe ciągi używając tylko skryptów powłoki.
Aby było jasne, jestem świadomy funkcji daty w Bash, ale to, czego szukam, to odpowiednik funkcji SPRINTF w C.
3 answers
W Bash:
var=$(printf 'FILE=_%s_%s.dat' "$val1" "$val2")
Lub, odpowiednik i bliższy sprintf
:
printf -v var 'FILE=_%s_%s.dat' "$val1" "$val2"
Jeśli Twoje zmienne zawierają wartości dziesiętne z początkowymi zerami, możesz je usunąć:
val1=008; val2=02
var=$(printf 'FILE=_%d_%d.dat' $((10#$val1)) $((10#$val2)))
Lub
printf -v var 'FILE=_%d_%d.dat' $((10#$val1)) $((10#$val2))
$((10#$val1))
wymusza wartość do bazy 10, więc %d
w specyfikacji formatu nie uważa, że "08" jest nieprawidłową wartością ósemkową.
Jeśli używasz date
(przynajmniej dla GNU date
), możesz pominąć początkowe zera w następujący sposób:
date '+FILE_%-m_%-d.dat'
Dla kompletność, jeśli chcesz dodać zera wiodące, wyściełane do pewnej szerokości:
val1=8; val2=2
printf -v var 'FILE=_%04d_%06d.dat' "$val1" "$val2"
Lub o szerokościach dynamicznych:
val1=8; val2=2
width1=4; width2=6
printf -v var 'FILE=_%0*d_%0*d.dat' "$width1" "$val1" "$width2" "$val2"
Dodawanie początkowych zer jest przydatne do tworzenia wartości, które łatwo sortują i wyrównują w kolumnach.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-10-13 23:00:44
Dlaczego nie używać programu printf z coreutils?
$ printf "FILE_%02d_%02d.dat" 1 2
FILE_01_02.dat
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2010-12-07 14:50:56
Try:
sprintf() { local stdin; read -d '' -u 0 stdin; printf "$@" "$stdin"; }
Przykład:
$ echo bar | sprintf "foo %s"
foo bar
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-10-13 22:28:12