grep sur une variable


58

Disons que j'ai une variable

line="This is where we select from a table."

Maintenant, je veux dire combien de fois la phrase est sélectionnée.

grep -ci "select" $line

J'ai essayé ça, mais ça n'a pas marché. J'ai aussi essayé

grep -ci "select" "$line"

Cela ne fonctionne toujours pas. Je reçois l'erreur suivante.

grep: This is where we select from a table.: No such file or directory

1
Vous devez utiliser herestring ...<<<"$line" . La commande grepattend un fichier à la place
Valentin Bajrami

Réponses:


85

J'ai greplu sur son entrée standard. Voilà, en utilisant une pipe ...

$ echo "$line" | grep select

... ou une chaîne ici ...

$ grep select <<< "$line"

Aussi, vous voudrez peut-être remplacer les espaces par des nouvelles lignes avant grepping:

$ echo "$line" | tr ' ' '\n' | grep select

... ou vous pouvez demander grepd'imprimer le match uniquement:

$ echo "$line" | grep -o select

Cela vous permettra de vous débarrasser du reste de la ligne quand il y a correspondance.

Edit: Oups, lisez un peu trop vite, merci Marco . Pour compter les occurrences, il suffit d’en diriger l’une d’elles vers wc(1);)

Une autre édition faite après le commentaire de lzkata , citant $linelors de l’utilisation echo.


3
Puisque l'OP veut compter le nombre d'occurrences d'une chaîne, vous pouvez ajouter un wcpour compléter la tâche:grep -o <string> <<< "$variable" | wc -l
Marco

2
Utilisez cette echo "$line"tr
option

Quelle est la disponibilité d'une chaîne Here? Cela nécessite-t-il Bash ou un autre shell?

Selon Wikipedia , ici les chaînes sont disponibles en bash, ksh et zsh (mais je suppose qu'il peut y en avoir d'autres).
John WH Smith

7
test=$line i=0
while case "$test" in (*select*)
test=${test#*select};;(*) ! :;;
esac; do i=$(($i+1)); done

Vous n'avez pas besoin d'appeler greppour une chose aussi simple.

Ou en fonction:

occur() while case "$1" in (*"$2"*) set -- \
        "${1#*"$2"}" "$2" "${3:-0}" "$((${4:-0}+1))";;
        (*) return "$((${4:-0}<${3:-1}))";;esac
        do : "${_occur:+$((_occur=$4))}";done

Il faut 2 ou 3 arguments. Fournir plus que cela faussera ses résultats. Vous pouvez l'utiliser comme:

_occur=0; occur ... . 2 && echo "count: $_occur"

... qui affiche le nombre d'occurrences .dans ...s'il se produit au moins 2 fois. Comme ça:

count: 3

Si $_occurest vide ou unsetlorsqu'il est appelé, cela n'affectera aucune variable shell et return1 si "$2"survient "$1"moins de "$3"fois. Ou, si elle est appelée avec seulement deux arguments, elle ne sera return1 que si elle "$2"n’est pas insérée "$1". Sinon, il retourne 0.

Et ainsi, dans sa forme la plus simple, vous pouvez faire:

occur '' . && echo yay || echo shite

... qui imprime ...

shite

...mais...

occur . . && echo yay || echo shite

... imprimera ...

yay

Vous pouvez également l'écrire un peu différemment et omettre les guillemets $2dans l' instruction (*"$2"*)and "${1#*"$2"}". Si vous faites cela, vous pouvez utiliser des globes de shell pour les correspondances comme sh[io]tepour le test de correspondance.


1
+1: plus rapide, en effet. Fonctionne dans bashet dash/ sh(et probablement quelques autres).
John WH Smith

@JohnWHSmith - le montage est meilleur, mais toujours aussi portable.
mikeserv
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.