[gull] Truc et astuces: bash: jouons avec les variables et eval

Félix Hauri felix at f-hauri.ch
Mon Nov 7 09:16:03 CET 2011


A propos de sed...

On Sat, Nov 05, 2011 at 10:57:15AM +0100, Félix Hauri wrote:
> Merci, mais je me disais qu'on *doit* pouvoir faire plus ``simple''...
> (sed est un outil puissant!)
> 
> $ eval $(
>     env LANG=fr_CH date +"$(
> 	date --help |
> 	    sed -ne '/^  %[^ %]\{1,4\} .*$/{
>                 s/^ *%\([^ ]*\) .*$/DATE_\1=\"%\1\"/;
> 		:l;
> 		/[^:%]:/{
> 		    s/:/_/;
> 		    tl};
> 		p}'
> 	)"
>     )
> $ echo $DATE_{x,X}
> 05. 11. 11 10:33:40

Encore plus simple!?
En fait, sed est autant puissant qui n'est pas facile à digérer.

 ``t'' est un branchement conditionnel, qui ne sera effectué que
       si le dernier s/// à matché un truc.
donc le pré-test et les accolades ne sont pas utiles:

$ eval $(
    env LANG=C date -d '2010-2-1 01:23:45' +"$(
	date --help | sed -ne \
 '/^  %[^%]* /{s/^ *%\([^ ]*\) .*$/DATE_\1=\"%\1\"/;::;s/\([^:%]\):/\1_/;t:;p}'
)")

Et boum, ma commande sed fait moins de 80 caractères (fax compatible;)

(pour faire de l'obsfuscation, je me suis contenté de nommer le label ``:'':
   Le symbole ``:'' est utilisé pour signalé un label pour un prochain branchement
   Donc ``::'' signale un point de branchement nommé ``:'', puis ``t:''
   est un branchement conditionnel qui ne sera effectué que si ``s/\([^:%]\):/...''
   à modifié quelque chose.
;)

$ ds='/^  %[^%]* /{s/^ *%\([^ ]*\) .*$/DATE_\1=\"%\1\"/;::;s/\([^:%]\):/\1_/;t:;p}'
$ date --help | sed -ne "$ds"
$ date +"$(date --help | sed -ne "$ds")"
$ eval $(date +"$(date --help | sed -ne "$ds")")

--
 Félix Hauri  -  <felix at f-hauri.ch>  -  http://www.f-hauri.ch


More information about the gull mailing list