Bash Expression régulière - Ne semble pas correspondre à \ s, \ S, etc.
J'ai un script qui tente d'obtenir des blocs d'informations à partir de gparted.
Mon apparence des Données:
Disk /dev/sda: 42.9GB
Sector size (logical/physical): 512B/512B
Partition Table: msdos
Number Start End Size Type File system Flags
1 1049kB 316MB 315MB primary ext4 boot
2 316MB 38.7GB 38.4GB primary ext4
3 38.7GB 42.9GB 4228MB primary linux-swap(v1)
log4net.xml
Model: VMware Virtual disk (scsi)
Disk /dev/sdb: 42.9GB
Sector size (logical/physical): 512B/512B
Partition Table: msdos
Number Start End Size Type File system Flags
1 1049kB 316MB 315MB primary ext4 boot
5 316MB 38.7GB 38.4GB primary ext4
6 38.7GB 42.9GB 4228MB primary linux-swap(v1)
- Je utiliser une regex pour briser ce en deux blocs de Disque
^De disque (/dev[\S]+):((?!Le disque)[\s\S])*
Cela fonctionne avec multiligne.
Quand j'ai tester cela dans un script bash, je ne semble pas correspondre \s, \S -- Ce que je fais mal?
Je suis en train de tester ce par le biais d'un script comme:
data=`cat disks.txt`
morematches=1
x=0
regex="^Disk (/dev[\S]+):((?!Disk)[\s\S])*"
if [[ $data =~ $regex ]]; then
echo "Matched"
while [ $morematches == 1 ]
do
x=$[x+1]
if [[ ${BASH_REMATCH[x]} != "" ]]; then
echo $x "matched" ${BASH_REMATCH[x]}
else
echo $x "Did not match"
morematches=0;
fi
done
fi
Cependant, quand je marche à travers les tests de parties de l'expression régulière, Chaque fois que je correspond a \s \S, il ne fonctionne pas -- ce que je fais mal?
source d'informationauteur Yablargo
Vous devez vous connecter pour publier un commentaire.
Peut-être \S et \s n'est pas pris en charge ou que vous ne pouvez pas les placer autour de
[ ]
. Essayez d'utiliser ce format à la place:MODIFIER
Il semble que vous voulez vraiment obtenir les champs correspondants. J'ai fait le script plus simple pour cela, mais je ne suis pas sûr si c'est votre intention de sortie:
Qui produit
de
man bash
ERE ne supporte pas de look-ahead/derrière. Cependant vous les avez dans votre code (
(?!Disk)
).C'est pourquoi votre regex n'aurez pas de match comme vous l'avez prévu.
Je sais que vous avez déjà "résolu", mais d'origine de votre problème est probablement d'aussi simple que de ne pas citer les
$regex
dans votre test. c'est à dire:Bash extension variable sera tout simplement plop de la chaîne, et de l'espace dans votre original regex va casser test car:
est l'équivalent de:
et bash/test aura un moment de plaisir de l'interprétation d'un bonus d'argument, et pour tous ceux non cotées méta-caractères.
Rappelez-vous, bash n'est pas passer variables, il étend.
Aussi,
[\s\S]
est équivalent à.
c'est à dire, n'importe quel personnage. Sur ma coquille,[^\s]
fonctionne, mais pas[\S]
.Parce que c'est une commune de la FAQ, permettez-moi d'énumérer quelques-unes des constructions qui ne sont pas pris en charge dans Bash, et la façon de travailler autour d'eux, où il y a une solution simple.
Il y a plusieurs dialectes d'expressions régulières dans l'usage commun. Celle prise en charge par Bash est une variante des Expressions Régulières Étendues. Ceci est différent de par exemple, ce que beaucoup de en ligne regex testeurs de soutien, ce qui est souvent le plus moderne de Perl 5 /PCRE variante.
\d
\D
\s
\S
\w
\W
-- ceux-ci peuvent être remplacés par des caractères POSIX classe équivalents de[[:digit:]]
[^[:digit:]]
[[:space:]]
[^[:space:]]
[_[:alnum:]]
et[^_[:alnum:]]
respectivement. (Remarquez le dernier cas, où la[:alnum:]
POSIX classe de personnage est augmentée avec un trait de soulignement à être exactement équivalente à la Perl\w
de sténographie.)a.*?b
avec quelque chose commea[^ab]*b
pour obtenir un effet similaire dans la pratique, bien que les deux ne sont pas exactement équivalents.(?<=before)
ou(?!after)
et en fait n'importe quoi avec(?
est une extension Perl. Il n'y a pas plus simple solution de contournement pour ceux-ci, bien que vous pouvez souvent reformuler votre problème à l'un où lookarounds peut être évité.