GNU/Linux >> Tutoriels Linux >  >> Linux

Extraire la valeur entre deux modèles de recherche sur la même ligne ?

J'ai ce qui suit dans un fichier Output.dat. J'ai besoin d'extraire la valeur entre dn: uid= et ,ou=

 dn: uid=user1,ou=Active,ou=Member,dc=domain,dc=org
 dn: [email protected],ou=Active,ou=Member,dc=domain,dc=org
 dn: uid=usertest,ou=Active,ou=Member,dc=domain,dc=org
 dn: uid=abc1,ou=Active,ou=Member,dc=domain,dc=org
  • J'ai essayé d'utiliser
    sed -e '/dn: uid=/,/,ou=/p' output.dat but
    

    il renvoie la ligne complète au lieu de la valeur.

  • Lorsque vous essayez d'utiliser
    sed -e '/dn: uid=/,/,ou=/1/p' output.dat
    

    puis j'ai eu l'erreur suivante :

    sed: -e expression #1, char 18: unknown command: `'
    

Réponse acceptée :

Si vous avez une version de GNU grep avec PCRE (-P ) support, alors en supposant que vous vouliez dire le premier occurrence de ,ou

grep -oP '(?<=dn: uid=).+?(?=,ou=)' file

Si vous voulez correspondre à la seconde ,ou vous pouvez supprimer le ? non gourmand modificateur

grep -oP '(?<=dn: uid=).+(?=,ou=)' file

Les expressions entre parenthèses sont des assertions de longueur nulle (alias lookarounds ) ce qui signifie qu'ils font partie du match, mais ne sont pas renvoyés dans le cadre du résultat. Vous pouvez faire la même chose nativement en perl, par exemple

perl -ne 'print "$1n" if /(?<=dn: uid=)(.+?)(?=,ou=)/' file 

Il est possible de faire quelque chose de similaire dans sed, en utilisant un groupement régulier (non de longueur nulle), par ex. (pour GNU sed - d'autres variétés peuvent nécessiter un échappement supplémentaire)

sed -rn 's/(.*dn: uid=)([^,]+)(,ou=.*)/2/p' file

ou en simplifiant légèrement

sed -rn 's/.*dn: uid=([^,]+),ou=.*/1/p' file

Notez le [^,] est un peu un hack ici, car sed n'a pas de véritable option de correspondance non gourmande.

Réflexion après coup  :bien que ce ne soit pas exactement ce que vous avez demandé, il semble que ce que vous voulez réellement faire est de lire name=value séparé par des virgules paires d'un fichier, puis séparez davantage la valeur du premier champ de son nom. Vous pouvez y parvenir de plusieurs façons, y compris

awk -F, '{sub(".*=","",$1); print $1}' file

ou une solution purement bash telle que

while IFS=, read -r a b c d; do printf '%sn' "${a#*=}"; done < file 

Linux
  1. Utilisation de Sed pour rechercher et remplacer une ligne entre des plages de motifs

  2. Imprimer des lignes entre (et en excluant) deux motifs ?

  3. Imprimer des lignes entre (et y compris) deux motifs ?

  4. Comment insérer du texte avant la première ligne d'un fichier ?

  5. Extraire du texte entre deux lignes spécifiques ?

Comment extraire le fichier tar.gz sous Linux à l'aide de la ligne de commande

Comment supprimer des lignes d'un fichier à l'aide de la commande Sed

Comment extraire le fichier Tar.xz sur la ligne de commande Linux

Tutoriel Unix Sed :Impression de lignes de fichier à l'aide d'adresses et de modèles

sed :comment remplacer la ligne si elle est trouvée ou ajouter à la fin du fichier si elle n'est pas trouvée ?

Différence d'espace entre deux fichiers sous Linux