Pascal BEAUSSART

Les modèles (patern)


Les modéles sont une chaine de caractères interprétée par le kornshell.
Les crochets [ ] délimitent un jeu de caractères entrant dans la définition d'un modèle.

A l'intérieur des crochets, les caractères - ! et \ ont des significations particulières :
- Permet de définir une suite de caractères :
Ainsi, [a-c] remplace positionnellement un caractère par a, b ou c.
[a-c][12] signifie dans l'ordre : a1 a2 b1 b2 c1 c2
! Inverse la signification. Ainsi [!a-c] signifie tout sauf a, b ou c.
\ Permet d'éviter de traduire le caractère qui le suit immédiatement après.
Ainsi, [\-\[\\\!\]] correspond à un des caractères parmis -[\!]

En dehors des crochets les caractères sont positionnels :
? Remplace n'importe quelle caractère (jocker)
* Zéro ou plusieurs caractères sont remplacé par l'étoile

Les modèles peuveut être combinés entre eux
?(modèle|modèle) Zéro ou une accurence de chaque modèle
*(modèle|modèle) Zéro ou plusieurs occurence de chaque modèle
+(modèle|modèle) Chaque caractères et au moins un, satisfont aux modèles
@(modèle|modèle) Une seule occurence pour chaque modèle
!(modèle|modèle) Aucune correspondance avec les modèles

Ne confondez pas modèle et expression régulière

Exemple de base


if [[ "$1" != X?([1-9]|[12][0-9]) ]]
then echo "Valeurs possibles : X, X1, X2, X3 .... X29"
fi
$1 peut prendre les valeurs X, X1, X2, X3 .... X29 mais pas X30


if [[ "$1" != ??([1]) ]]
then echo "Valeurs possibles :  N'importe quel caractère suivi ou pas du chiffre 1"
fi
$1 peut être égal à : A, 11, @1 ... mais pas A11 ou A2
Remarquer la signigication différente du point d'interrogation dans la même expression.
le premier est un jocker alors que le second précise zéro ou une répétition du modèle qui suit.


Exemple d'une fonction de validation d'un format de date jj/mm/aa ou jj/mm/aaaa :


verifie_date() {
  if [[ "$1" != @([1-9]|[0][1-9]|[12][0-9]|[3][01])@([/])@([1-9]|[1][0-2]|[0][1-9])@([/])@([0-9][0-9]?[0-9][0-9]) ]]
  then
       echo "***** format date erronné ****"
       rc=1
  else
       rc=0
  fi
  return $rc
}

Explication :

"jj" peut prendre les valeurs de 1 à 31 sur un ou deux digits.
Soit l'expression : @([1-9]|[0][1-9]|[12][0-9]|[3][01])

[1-9]     : 1, 2, 3, 4, 5, 6, 7, 8, 9
[0][1-9]  : 01, 02, 03, 04, 05, 06, 07, 08, 09
[12][0-9] : 1 ou 2 suivi d'un chiffre de 0 à 9 , soit de 10 à 29
[3][01]   : 30 ou 31

"mm" peut prendre les valeurs de 1 à 12 sur un ou deux digits.
Soit l'expression : @([1-9]|[1][0-2]|[0][1-9])

[1-9]     : 1, 2, 3, 4, 5, 6, 7, 8, 9
[1][0-2]  : 10, 11, 12
[0][1-9]  : 01, 02, 03, 04, 05, 06, 07, 08, 09

"aa" ou "aaaa" soit deux ou quatre digits.
Soit l'expression : @([0-9][0-9]?[0-9][0-9])

[0-9][0-9]  : de 00 à 99
?[0-9][0-9] : suivi éventuellement de deux chiffres 00 à 99

Les slashs "/" sont obligatoires :
Soit l'expression : @([/]) répétée à deux reprises.


Autre exemple facilement applicable à la commande "ls"

Supposons qu'il existe dans le répertoire courant, les fichiers : t ta taa taaa tae te tee ttt zzz
 ls ?           ==> t
 ls t?*         ==> ta taa taaa tae te tee ttt
 ls *e          ==> tae te tee
 ls t[ae]       ==> ta te 
?(modèle|modèle) zéro ou une accurence de chaque modèle
 ls t?([ae]|tt) ==> t ta te ttt 
*(modèle|modèle) zéro ou plusieurs occurence de chaque modèle
 ls t*([ae]|tt) ==> t ta taa taaa tae te tee ttt 
+(modèle|modèle) chaque caractères et au moins un, satisfont aux modèles
 ls t+([ae]|tt) ==> ta taa taaa tae te tee ttt 
@(modèle|modèle) une seule occurence pour chaque modèle
 ls t@([ae]|tt) ==> ta te ttt 
!(modèle|modèle) aucune correspondance avec les modèles
 ls t!([ae]|tt) ==> t taa taaa tae tee 


[RETOUR] [HOME]