Jen první výskyt z grep -o -P

Jen první výskyt z grep -o -P
« kdy: 07. 02. 2024, 11:31:55 »
Nemohu za boha přijít na to jak grepem vrátit jen první výskyt v jednořádkovém vstupu. -m1 nepomáhá. Jde to řešit jinak než  přidáním |head -n1 ? Z výkonnostních důvodů
« Poslední změna: 07. 02. 2024, 11:33:41 od Petr Krčmář »


RDa

  • *****
  • 2 709
    • Zobrazit profil
    • E-mail
Re:Jen první výskyt z grep -o -P
« Odpověď #1 kdy: 07. 02. 2024, 17:18:37 »
co treba neco, co vrati vyraz dle patternu nebo taky nic, pokud tam neni:

Kód: [Vybrat]
sed -E 's/^(.*)((regex)|())(.*)$/\2/'

mikrom

  • ****
  • 370
    • Zobrazit profil
    • E-mail
Re:Jen první výskyt z grep -o -P
« Odpověď #2 kdy: 07. 02. 2024, 21:02:29 »
Tak si na to napis skript, ze budes grepu v cykle davat na spracovanie po jednom subore a zakazdym checknes RC ci bol uspesny, alebo nie. V pripade uspechu ukoncis cyklus.

priblizne takto:
Kód: [Vybrat]
#!/bin/bash
search_string="foo bar"
files=$(ls *.txt)
for file in $files; do
    echo ".. searching for \"$search_string\" in file: $file"
    grep -m1 "$search_string" $file
    if [ $? -eq 0 ]; then
        echo "successful - breaking the loop"
        break
    fi 
done
« Poslední změna: 07. 02. 2024, 21:05:15 od mikrom »

e3k

  • ****
  • 259
    • Zobrazit profil
    • E-mail
Re:Jen první výskyt z grep -o -P
« Odpověď #3 kdy: 07. 02. 2024, 21:17:35 »
Nemohu za boha přijít na to jak grepem vrátit jen první výskyt v jednořádkovém vstupu. -m1 nepomáhá. Jde to řešit jinak než  přidáním |head -n1 ? Z výkonnostních důvodů
skus -m 1 namiesto -m1?

mikrom

  • ****
  • 370
    • Zobrazit profil
    • E-mail
Re:Jen první výskyt z grep -o -P
« Odpověď #4 kdy: 07. 02. 2024, 23:16:36 »
Nemohu za boha přijít na to jak grepem vrátit jen první výskyt v jednořádkovém vstupu. -m1 nepomáhá. Jde to řešit jinak než  přidáním |head -n1 ? Z výkonnostních důvodů
skus -m 1 namiesto -m1?
Pouzitie -m1 alebo -m 1 da to iste, t.j. prvy najdeny vyskyt v jednom subore. To znamena, ze ak grep prehladava viac suborov tak ku kazdemu suboru v ktorom najde nejake vyskyty vypise prvy, co vo vysledku znamena ze grep moze vratit viac ako jeden riadok.


Re:Jen první výskyt z grep -o -P / zadání doplněno
« Odpověď #5 kdy: 07. 02. 2024, 23:30:21 »
Dnes ty rady mi chodí uplně mimo, tak doplním zadání. Nepomohla ni první rada, nevrací mi to nic, upravil jsem to a zkusil přidat /gi flag nebo ubrat ^a$.

- Charakter grepování vyžaduje  volbu -o - když je to jeden řádek přeci :
- Taky ještě doplním/připomenu, že ten skript mi vrátí všechny výskyty (na co výskyt, to řádek) . Takže to |head -n1 řeší, jen je to pomalé.
- Taky jsem hledal elegantní řešení,  přímo aktérující na příkazu grep, nějaký jeden switch, než to přepíšu do awk
- Délka jednotlivých segmentů 40kB až 4MB, celková délka vstupu 300MB, ale tím tailem ji "seekuju" ..
Fakt, že vstup je jednořádkový znamená, že nanajvýš může být v jednom souboru. Kdyby byl v nula souborech , tak by nebylo co vstupovat. Ve skutečnosti je ale vstup z pípy (protože jsou z souboru odstraněny některé znaky jako  \n \r a mezery).

Přirozeně,  m mezera 1 nepomohlo.   :o Bohužel grep v tomhle má krev na rukou, protože volba se jmenuje --max-count, ale až man vysvětluje  vysvětluje, že se to týká řádků


Zjednodušený zadání: ale bojím, se , že to bude moc dlouhý, na to jak to ve skutečnosti je jednoduchý

Při každém použití  dávám různý parametr prvnímu příkazu tail, jde o append only soubor vstup.txt. Hledaný řetězec  začíná MAGIC (shodou okolností na začátku řádku, ještě před tr) a končí nějakým delimiterem . A rozprostírá se to přes víc řádků, proto ten mezikrok s tr.
tail -n8000 vstup.txt |  tr -d "\r\n " |grep -Po "MAGIC[^-]......"

vstup
echo ' dfjkfjk skhd ;jkh kjdjfh --- skjdfh sd ;khsdskjfjh ;jh h;kh --- ;kjh --- ;kjh ;kjh ;k ;'  |grep -Po ";[^-]+"

Prostě jednoduše: začíná to středníkem slovo a jede se až po první pomlčku. V tomhle vstupu jsou čtyri výsledky(=dá 4 rádky), já chci jen první, -m1 dá identický výstup.
Pozor, středník může být i uvnitř a stejně tak pomlčka může být i mimo zachytávný region a nic neznamená

jako mohou použít AWK asi(myslím, že na takovéhle výstřižky určené počátečním a koncovým patternem přímo umí, něco jako toggle a převzal to ruby |ruby -ne 'print if /StartToken/ ... /Konec/' ),  místo grepu, když to grep in-house neumí, doufal jsem ,že když -m1 nefunuje, že je nějaká analogogie jako -n1 když se neoperuje s řádky, ale s výskyty
« Poslední změna: 07. 02. 2024, 23:32:22 od Ħαℓ₸℮ℵ ␏⫢ ⦚ »

RDa

  • *****
  • 2 709
    • Zobrazit profil
    • E-mail
Re:Jen první výskyt z grep -o -P
« Odpověď #6 kdy: 08. 02. 2024, 00:34:19 »
Tak on ten sed i funguje, jen ten "or empty" ... "|()" musi byt na konci celeho vyrazu:

Kód: [Vybrat]
$ echo 'halabalaregexfujkyneregex?' | sed -E 's/^(((.*)(regex)(.*))|(.*))$/\4/'
regex
$ echo 'halabalarugexfujkynerugex?' | sed -E 's/^(((.*)(regex)(.*))|(.*))$/\4/'

$

Samozrejme to vraci i prazdni radek, ne prazdny vystup.

Skripty tohoto druhy opravdu nepisu v bashi, hlavne kdyz drobnost typu | head -n1 je vykonnosti problem.
A i v PHP si vstup sekam na mensi elementy, nez provadet nejake operace nad MB daty.

RDa

  • *****
  • 2 709
    • Zobrazit profil
    • E-mail
Re:Jen první výskyt z grep -o -P / zadání doplněno
« Odpověď #7 kdy: 08. 02. 2024, 00:37:45 »

vstup
echo ' dfjkfjk skhd ;jkh kjdjfh --- skjdfh sd ;khsdskjfjh ;jh h;kh --- ;kjh --- ;kjh ;kjh ;k ;'  |grep -Po ";[^-]+"

Prostě jednoduše: začíná to středníkem slovo a jede se až po první pomlčku. V tomhle vstupu jsou čtyri výsledky(=dá 4 rádky), já chci jen první, -m1 dá identický výstup.
Pozor, středník může být i uvnitř a stejně tak pomlčka může být i mimo zachytávný region a nic neznamená


tak nechapu proc mazes pres tr ty newlines, kdybys tam proved tr ";" "\n", tak si to muzes zpracovat skrze -m1 (stop after 1 matching line)

mikrom

  • ****
  • 370
    • Zobrazit profil
    • E-mail
Re:Jen první výskyt z grep -o -P / zadání doplněno
« Odpověď #8 kdy: 08. 02. 2024, 01:27:19 »
vstup
echo ' dfjkfjk skhd ;jkh kjdjfh --- skjdfh sd ;khsdskjfjh ;jh h;kh --- ;kjh --- ;kjh ;kjh ;k ;'  |grep -Po ";[^-]+"

skusil som cez awk:

echo ' dfjkfjk skhd ;jkh kjdjfh --- skjdfh sd ;khsdskjfjh ;jh h;kh --- ;kjh --- ;kjh ;kjh ;k ;'  | awk 'BEGIN {RS="---"; FS=";"} {for(i=2; i<=NF; i++) printf(";%s",$i); print(""); exit}'

vysledok:
;jkh kjdjfh

Re:Jen první výskyt z grep -o -P
« Odpověď #9 kdy: 08. 02. 2024, 09:32:55 »
první výskyt v jednořádkovém vstupu

grep -o -m1 word <<< $(echo 'First word, second word.' | grep -o word)