[gelöst] Pattern per Variable an egrep geben

Vom einfachen Programm zum fertigen Debian-Paket, Fragen rund um Programmiersprachen, Scripting und Lizenzierung.
Antworten
Benutzeravatar
Duff
Beiträge: 6321
Registriert: 22.03.2005 14:36:03
Wohnort: /home/duff

[gelöst] Pattern per Variable an egrep geben

Beitrag von Duff » 19.02.2009 11:30:17

Hallo,

ich möchte in einem Skript an egrep einen bestimmten Suchpattern übergeben.
Der Suchpattern ist so aufgebaut: $P="'(Pattern1 |Pattern2 |Pattern3 )'"

Mache ich nun ein egrep $P datei, kommt nichts zurück. Mache ich allerdings ein egrep '(Pattern1 |Pattern2 |Pattern3 )' datei, erhalte ich ein Ergebnis.


Kann den Fehler nicht finden. Das OS ist ein HP-UX.


Danke & Gruß,
Daniel
Zuletzt geändert von Duff am 19.02.2009 17:30:49, insgesamt 1-mal geändert.
Oh, yeah!

Benutzeravatar
Meillo
Moderator
Beiträge: 9254
Registriert: 21.06.2005 14:55:06
Wohnort: Balmora
Kontaktdaten:

Re: Pattern per Variable an egrep geben

Beitrag von Meillo » 19.02.2009 12:59:21

so hat's bei mir funktioniert:

Code: Alles auswählen

$ a='(Pattern1 |Pattern2 |meillo)'

$ egrep "$a" /etc/passwd
meillo:x:1000:1000:meillo,,,:/home/meillo:/bin/bash
Also nur die Quotes anders verwendet.
Use ed once in a while!

Benutzeravatar
Duff
Beiträge: 6321
Registriert: 22.03.2005 14:36:03
Wohnort: /home/duff

Re: Pattern per Variable an egrep geben

Beitrag von Duff » 19.02.2009 13:41:51

Danke, hatte ich auch schon probiert.
Es wird dann aber leider nichts gefunden.

Verstehe es nicht...
Oh, yeah!

Benutzeravatar
habakug
Moderator
Beiträge: 4314
Registriert: 23.10.2004 13:08:41
Lizenz eigener Beiträge: MIT Lizenz

Re: Pattern per Variable an egrep geben

Beitrag von habakug » 19.02.2009 14:17:32

Hallo!

So geht es hier:

Code: Alles auswählen

work@lenny64:~$ a='mysql|ftp|nobody|Gott'
work@lenny64:~$ egrep $a /etc/passwd
nobody:x:65534:65534:nobody:/nonexistent:/bin/sh
ftp:x:115:65534::/home/ftp:/bin/false
mysql:x:117:124:MySQL Server,,,:/var/lib/mysql:/bin/false
Gruß, habakug
( # = root | $ = user | !! = mod ) (Vor der PN) (Debianforum-Wiki) (NoPaste)

Benutzeravatar
Duff
Beiträge: 6321
Registriert: 22.03.2005 14:36:03
Wohnort: /home/duff

Re: Pattern per Variable an egrep geben

Beitrag von Duff » 19.02.2009 14:19:02

Das komische ist, trage ich den Pattern händisch in eine Variable, funktioniert es.

Code: Alles auswählen

STRING=$(echo ${ARRAY[@]}|sed -ne 's/ /|/pg'| sed -ne "s/\(.*\)/'(\1)'/p")
echo $STRING
STRING='(Pattern.1_|Pattern.2_|Pattern.3_)'
Mit String (1) funktioniert es nicht beim egrep-Befehl und mit String (2) funktioniert es, obwohl ein echo des Strings (1) identisch zu String (2) aussieht.
Oh, yeah!

Benutzeravatar
habakug
Moderator
Beiträge: 4314
Registriert: 23.10.2004 13:08:41
Lizenz eigener Beiträge: MIT Lizenz

Re: Pattern per Variable an egrep geben

Beitrag von habakug » 19.02.2009 14:35:43

Hallo!

Nein, das geht so;

Code: Alles auswählen

work@lenny64:~$ ARRAY=(one two three)
work@lenny64:~$ echo ${ARRAY[*]}
one two three
work@lenny64:~$ echo $ARRAY[*]
one[*]
work@lenny64:~$ echo ${ARRAY[2]}
three
work@lenny64:~$ ARRAY[3]=four
work@lenny64:~$ echo ${ARRAY[*]}
one two three four
Gruß, habakug

http://tldp.org/LDP/Bash-Beginners-Guid ... 10_02.html
( # = root | $ = user | !! = mod ) (Vor der PN) (Debianforum-Wiki) (NoPaste)

Benutzeravatar
Meillo
Moderator
Beiträge: 9254
Registriert: 21.06.2005 14:55:06
Wohnort: Balmora
Kontaktdaten:

Re: Pattern per Variable an egrep geben

Beitrag von Meillo » 19.02.2009 15:53:47

Duff hat geschrieben:Verstehe es nicht...
Ich nach einigem Rumspielen auch nicht so recht ... bis ich mal `set -x' verwendete.
Dann jedoch wunderte ich mich über die rätselhaften Singlequotes um die Leerzeichen.
Ohne Leerzeichen in der Regexp funktioniert's bei mir:

Code: Alles auswählen

$ a="(Pattern1|Pattern2|meillo)"
+ a='(Pattern1|Pattern2|meillo)'

$ egrep  -e $a /etc/passwd
+ egrep -e '(Pattern1|Pattern2|meillo)' /etc/passwd
meillo:x:1000:1000:meillo,,,:/home/meillo:/bin/bash
Use ed once in a while!

Benutzeravatar
Duff
Beiträge: 6321
Registriert: 22.03.2005 14:36:03
Wohnort: /home/duff

Re: Pattern per Variable an egrep geben

Beitrag von Duff » 19.02.2009 16:45:47

Wenn ich die Patterns nicht in einem Array speicher und mit anschließend mit sed bearbeite, sondern händisch in die Variable eintrage, funktioniert es bei mir auch.

(Problem ist weiter oben beschrieben).


Ich kann den Such-Pattern leider nicht hartverdrahtet in einer Variablen speichern, da ich diesen Such-Pattern erst noch durch vorherige grep's zusammen bauen muss.

(Hoffe, es versteht noch jemand, was ich meine ;-) )
Oh, yeah!

Benutzeravatar
Meillo
Moderator
Beiträge: 9254
Registriert: 21.06.2005 14:55:06
Wohnort: Balmora
Kontaktdaten:

Re: Pattern per Variable an egrep geben

Beitrag von Meillo » 19.02.2009 16:59:00

meinst du sowas:

Code: Alles auswählen

$ set -x
+ set -x

$ a1=aa
+ a1=aa

$ a2=bb
+ a2=bb

$ a3=`whoami`
+ a3=meillo

$ a="($a1|$a2|$a3)"
+ a='(aa|bb|meillo)'

$ egrep  $a /etc/passwd
+ egrep '(aa|bb|meillo)' /etc/passwd
meillo:x:1000:1000:meillo,,,:/home/meillo:/bin/bash
Oder soll auch der Inhalt von $a variabel sein?
Use ed once in a while!

Benutzeravatar
Duff
Beiträge: 6321
Registriert: 22.03.2005 14:36:03
Wohnort: /home/duff

Re: Pattern per Variable an egrep geben

Beitrag von Duff » 19.02.2009 17:16:49

Ja so in etwa.

Ich bin leider nicht mehr auf der Arbeit und habe somit kein HP-UX mehr zur Hand.

Ich vermute das Problem im Speichern der einzelnen Pattern's im Array. Aber sicher bin ich mir nicht.


So, habe mal ein Beispiel mit der bash reproduzieren können.

Das Beispiel Skript test.sh

Code: Alles auswählen

daniel@daniel-laptop:/tmp$ cat test.sh 
#!/bin/bash

declare -a ARRAY
pw=/etc/passwd
j=0;
for i in $(grep da $pw|awk -F":" '{print $1}')
do
	ARRAY[$j]=$i
	j=$((j+1))
done

PATTERN=$(echo ${ARRAY[*]}|sed -ne 's/ /|/gp'|sed -ne "s/\(.*\)/'(\1)'/p")
echo $PATTERN

egrep $PATTERN $pw

Das Skript test.sh bei der Ausführung und es kommt kein Ergebnis zurück beim grep-Befehl.

Code: Alles auswählen

daniel@daniel-laptop:/tmp$ ./test.sh 
'(daemon|www-data|haldaemon|daniel|avahi|davfs2)'
Setzt man allerdings den Pattern aus dem Skript händisch in einen grep-Befehl, so funktioniert es

Code: Alles auswählen

daniel@daniel-laptop:/tmp$ egrep '(daemon|www-data|haldaemon|daniel|avahi|davfs2)' /etc/passwd
daemon:x:1:1:daemon:/usr/sbin:/bin/sh
www-data:x:33:33:www-data:/var/www:/bin/sh
haldaemon:x:105:106:Hardware abstraction layer,,,:/var/run/hal:/bin/false
daniel:x:1000:1000:daniel,,,:/home/daniel:/bin/bash
avahi:x:110:115:Avahi mDNS daemon,,,:/var/run/avahi-daemon:/bin/false
davfs2:x:115:122::/var/cache/davfs2:/bin/false
Oh, yeah!

Benutzeravatar
Duff
Beiträge: 6321
Registriert: 22.03.2005 14:36:03
Wohnort: /home/duff

Re: Pattern per Variable an egrep geben

Beitrag von Duff » 19.02.2009 17:30:34

Wahnsinn...

...konnte nun endlich den Fehler finden.

Code: Alles auswählen

...
++ sed -ne 's/ /|/gp'
++ sed -ne 's/\(.*\)/'\''(\1)'\''/p'
+ PATTERN=''\''(daemon|www-data|haldaemon|daniel|avahi|davfs2)'\'''
+ echo ''\''(daemon|www-data|haldaemon|daniel|avahi|davfs2)'\'''
'(daemon|www-data|haldaemon|daniel|avahi|davfs2)'
+ egrep ''\''(daemon|www-data|haldaemon|daniel|avahi|davfs2)'\''' /etc/passwd

Sprich, es wurde dem grep-Befehl zu viele '-Zeichen übergeben.

Habe es nun wie folgt gelöst:

Code: Alles auswählen

#!/bin/bash
#set -x
declare -a ARRAY
pw=/etc/passwd
j=0;
for i in $(grep da $pw|awk -F":" '{print $1}')
do
	ARRAY[$j]=$i
	j=$((j+1))
done

PATTERN=$(echo ${ARRAY[*]}|sed -ne 's/ /|/gp'|sed -ne "s/\(.*\)/(\1)/p")
echo $PATTERN

egrep $PATTERN $pw
Das Ergebnis vom grep-Befehl...

Code: Alles auswählen

daniel@daniel-laptop:/tmp$ ./test.sh 
(daemon|www-data|haldaemon|daniel|avahi|davfs2)
daemon:x:1:1:daemon:/usr/sbin:/bin/sh
www-data:x:33:33:www-data:/var/www:/bin/sh
haldaemon:x:105:106:Hardware abstraction layer,,,:/var/run/hal:/bin/false
daniel:x:1000:1000:daniel,,,:/home/daniel:/bin/bash
avahi:x:110:115:Avahi mDNS daemon,,,:/var/run/avahi-daemon:/bin/false
davfs2:x:115:122::/var/cache/davfs2:/bin/false
Nochmals Danke an alle, die mir geholfen haben...
Oh, yeah!

Benutzeravatar
Meillo
Moderator
Beiträge: 9254
Registriert: 21.06.2005 14:55:06
Wohnort: Balmora
Kontaktdaten:

Re: Pattern per Variable an egrep geben

Beitrag von Meillo » 19.02.2009 17:35:20

Duff hat geschrieben:So, habe mal ein Beispiel mit der bash reproduzieren können.

Das Beispiel Skript test.sh
Ich habe dein Script genommen und etwas umgebaut (ich mag Arrays in der Shell einfach nicht).

Folgendes tut in bash, dash und ksh:

Code: Alles auswählen

#!/bin/bash

set -x  # for debug output

pw=/etc/passwd
for i in `grep da $pw|cut -d: -f1` ; do
        pat="$pat|$i"
done

PATTERN=`echo $pat|sed 's/^|/(/ ; s/$/)/'`
echo $PATTERN

egrep $PATTERN $pw
Use ed once in a while!

Benutzeravatar
habakug
Moderator
Beiträge: 4314
Registriert: 23.10.2004 13:08:41
Lizenz eigener Beiträge: MIT Lizenz

Re: [gelöst] Pattern per Variable an egrep geben

Beitrag von habakug » 19.02.2009 18:49:27

Hallo!

Ich hätte es so gemacht:

Code: Alles auswählen

#!/bin/bash
#set -x
declare -a ARRAY
pw=/etc/passwd
j=0
for i in $(grep da $pw|awk -F":" '{print $1}')
do
   ARRAY[$j]=$i
   j=$((j+1))
   egrep ${ARRAY[$j-1]} $pw
done
...obwohl ich keinen Kirschkuchen mag, viel zu sauer, da hilft noch nicht mal haufenweise Schlagsahne.

Gruß, habakug
( # = root | $ = user | !! = mod ) (Vor der PN) (Debianforum-Wiki) (NoPaste)

Benutzeravatar
Duff
Beiträge: 6321
Registriert: 22.03.2005 14:36:03
Wohnort: /home/duff

Re: [gelöst] Pattern per Variable an egrep geben

Beitrag von Duff » 20.02.2009 09:15:41

Danke für die beiden anderen Varianten (viele Wege führen nach Rom ;-))

Aber was spricht gegen Array's?
Oh, yeah!

Benutzeravatar
Meillo
Moderator
Beiträge: 9254
Registriert: 21.06.2005 14:55:06
Wohnort: Balmora
Kontaktdaten:

Re: [gelöst] Pattern per Variable an egrep geben

Beitrag von Meillo » 20.02.2009 09:53:17

Duff hat geschrieben:Aber was spricht gegen Array's?
Mir ist nicht bekannt dass die portabel wären. In der SUSv3 steht jedenfalls nichts von ihnen:

Code: Alles auswählen

wget -O - http://www.opengroup.org/onlinepubs/009695399/utilities/xcu_chap02.html#tag_02  | grep -i array
Use ed once in a while!

Benutzeravatar
Duff
Beiträge: 6321
Registriert: 22.03.2005 14:36:03
Wohnort: /home/duff

Re: [gelöst] Pattern per Variable an egrep geben

Beitrag von Duff » 20.02.2009 11:06:16

Ok, aber was verstehst du genau unter "portabel"?
Oh, yeah!

Benutzeravatar
Meillo
Moderator
Beiträge: 9254
Registriert: 21.06.2005 14:55:06
Wohnort: Balmora
Kontaktdaten:

Re: [gelöst] Pattern per Variable an egrep geben

Beitrag von Meillo » 20.02.2009 11:10:24

Duff hat geschrieben:Ok, aber was verstehst du genau unter "portabel"?
Funktioniert mit allen `sh'-kompatiblen Shells ... das kleinste gemeinsame Vielfache also. Ich versuche ``bashism'' zu vermeiden.

Wenn man davon ausgeht, dass die `bash' überall verfügbar ist, dann ist Arrays sicher kein Problem.
Use ed once in a while!

Benutzeravatar
Duff
Beiträge: 6321
Registriert: 22.03.2005 14:36:03
Wohnort: /home/duff

Re: [gelöst] Pattern per Variable an egrep geben

Beitrag von Duff » 20.02.2009 15:44:34

Aber arrays kann ich selbst unter hp-ux 11.11 mit der ksh benutzen. Unter solaris denke ich aber auch. Könnte ich mal probieren.
Oh, yeah!

Benutzeravatar
Meillo
Moderator
Beiträge: 9254
Registriert: 21.06.2005 14:55:06
Wohnort: Balmora
Kontaktdaten:

Re: [gelöst] Pattern per Variable an egrep geben

Beitrag von Meillo » 20.02.2009 15:47:33

Duff hat geschrieben:Aber arrays kann ich selbst unter hp-ux 11.11 mit der ksh benutzen. Unter solaris denke ich aber auch. Könnte ich mal probieren.
Strings kannst du ganz sicher überall nutzen ... wenn's damit auch geht (ohne unnötig komplizierter zu sein), warum nicht diese portablere Lösung wählen?

Aber gut, das ist auch ein bisschen Einstellung und Ansichtssache. Somit solltest du dir darüber nicht zu viel Gedanken machen, wenn Arrays für dich okay sind.
Use ed once in a while!

Benutzeravatar
Duff
Beiträge: 6321
Registriert: 22.03.2005 14:36:03
Wohnort: /home/duff

Re: [gelöst] Pattern per Variable an egrep geben

Beitrag von Duff » 20.02.2009 16:02:17

Werde mal versuchen deinen Rat zu folgen.

Aber mal schauen, wie lange es dauert bis ich doch wieder auf arrays zurück greifen werde...

;-)
Oh, yeah!

Antworten