извлекать текст из файла с помощью терминала?

Для меня это был раздел, который был установлен в папке, принадлежащей root, а другие не имели прав на запись

drwxr-xr-x 22 root    root    4096 Sep 17 01:31 data

Таким образом, папка мусора не могла быть создана в верхней папке

Я только что изменил права доступа к папке, где был установлен раздел .... и вуаля, это сработало !!!!

sudo chmod 777 data
1
задан 7 November 2014 в 21:07

3 ответа

Например:

 egrep "id_ad=[[:digit:]]+&action" file.txt |  tr "=&" "  " | cut -d " " -f2 

... но я уверен, что есть более элегантные способы ;-).

Шаг за шагом:

egrep "id_ad=[[:digit:]]+&action" file.txt 

сканирование file.txt для шаблона (регулярное выражение), которое составлено литералом id_ad=, за которым следуют 1 или более цифр ( значение [[:digit:]]+, за которым следует буква &action. Отправьте вывод на стандартный вывод.

tr "=&" "  " 

преобразует символы «=» и «& amp;» в два пробела.

cut -d " " -f2

распечатать второе поле (разделенное пробелом) стандартного ввода.

2
ответ дан 24 May 2018 в 02:07
  • 1
    Благодаря! Можете ли вы объяснить, почему: цифра: внутри двойных квадратных скобок, пожалуйста? Я предполагаю, что внутренняя скобка - это просто часть указанной структуры, в то время как внешняя - это то, что говорит, что мы сопоставляем ее (в то время как левые и правые литералы не заключены в скобки, поэтому не совпадают ???). Я близко? – bcsteeve 7 November 2014 в 00:29
  • 2
    Нет, это просто синтаксис регулярного выражения, используемого egrep. См. [F2], прокрутите вниз до «Классы символов и выражения скобок». – Rmano 7 November 2014 в 01:07
  • 3
    ergep устарел, вместо этого используйте grep -E. – Avinash Raj 8 November 2014 в 06:57

С sed:

sed 's/id_ad=\(.*\)&action/\1/' filename

Объяснение:

Команда выше возвращает любые строки (.*) между двумя словами START (id_ad=) и END (&action ]) в имени файла. \(...\) Используется для захвата групп. \( - начало группы захвата и заканчивается на \). И с \1 мы печатаем его индекс группы (у нас есть одна группа захвата)

. Лучшая команда sed для вышеуказанного решения может быть такой:

sed 's/^id_ad=\([0-9]*\)&action/\1/' filename

^ Начало строки. [0-9]*: Любое число с 0 или более вхождениями. Подробнее о команде sed

С grep:

Объяснение:

grep -Po '(?<=id_ad=)[0-9]*(?=&action)' filename

От man grep:

-o, --only-matching
      Print only the matched (non-empty) parts of a matching line,
      with each such part on a separate output line.
-P, --perl-regexp
      Interpret PATTERN as a Perl compatible regular expression (PCRE)

Возвращает любое число с 0 или более вхождений ([0-9]*) между двумя словами START (id_ad=) и END word (&action) в имени файла.

(?<=pattern): положительный Lookbehind. Пара круглых скобок с открывающей скобкой, за которой следует знак вопроса, символ «меньше» и знак равенства.

(?<=id_ad=)[0-9]* (положительный lookbehind) соответствует 0 или более числам чисел, которые следуют после id_ad= в имени файла.

(?=pattern): Положительный Lookahead: Положительная конструкция lookahead представляет собой пару круглых скобок с открывающей скобкой, за которой следует знак вопроса и знак равенства.

[0-9]*(?=&action): (положительный lookahead) соответствует 0 или более вхождений чисел, за которыми следует шаблон (&action), не делая шаблон (&action) частью совпадения. Подробнее о команде sed

Дополнительные ссылки: Подробнее см. в команде sed GREP для дизайнеров

2
ответ дан 24 May 2018 в 02:07
  • 1
    Предоставление объяснений было бы хорошим, особенно когда человек, который задал вопрос, часами искал, как это сделать. – Alaa Ali 7 November 2014 в 01:51
  • 2
    С sed вам нужно хотя бы использовать ключ -n и просто распечатать замену, я думаю, i.e. sed -n 's/id_ad=\(.*\)&action/\1/p' (в противном случае sed печатает все строки по умолчанию), хотя лично я бы сделал совпадение более конкретным, например. `sed -n 's / ^ id_ad = ([0-9] *) & amp; action / \ 1 / p' – steeldriver 7 November 2014 в 02:43
  • 3
    @ Kasiya, как сказал steeldriver, ваше решение sed не будет работать, если два или более id_ad=00&action присутствуют в одной строке. – Avinash Raj 8 November 2014 в 06:59
  • 4
    И вам не нужно идти искать. Этого grep -Po 'id_ad=\K[0-9]*(?=&action)' filename было бы достаточно. – Avinash Raj 8 November 2014 в 07:00

Другой ответ python через модуль re. Пример, украденный из сообщения Джейкоба.

script.py

#!/usr/bin/python3
import sys
import re
file = sys.argv[1]
L = []                                                  # Declare an empty list
with open(file) as src:
    for j in src:                                       # iterate through all the lines
        for i in re.findall(r'id_ad=(\d+)&action', j):  # extracts the digits which was present in-between `id_ad=` and `&action` strings.
            L.append(i)                                 # Append the extracted digits to the already declared empty list L. 
    for f in L:                                         # Iterate through all the elements in the list L
        print(f)                                        # Print each element from the list L in a separate new line.

Запустите указанный скрипт как

python3 script.py /path/to/the/file

Пример:

$ cat fi
I want to process the body of text and extract an integer from a specific position in the text, but I'm not sure how to describe that 'particular position'. Regular expressions really confuse me. I spent (wasted) a couple hours reading tutorials and I feel no closer to an answer :( There's a bunch of text which may or may not include integers (that I don't want) and then there's a line that always contains

 id_ad=1929170&action There's a bunch of text which may or may not include integers (that I don't want) and then there's a line that always contains id_ad=1889170&action and then followed by a bunch of garbage I don't care about, again it may or may not include one or more integers. There's a bunch of text which may or may not include integers (that I don't want) and then there's a line that always contains

 id_ad=1889170&action and then followed by a bunch of garbage I don't care about, again it may or may not include one or more integers. There's a bunch of text which may or may not include integers (that I don't want) and then there's a line that always contains id_ad=1929990&action
$ python3 script.py ~/file
1929170
1889170
1889170
1929990
1
ответ дан 24 May 2018 в 02:07
  • 1
    Я тестировал его, на больших файлах, это становится быстрее, спасибо, что упомянули об этом. – Jacob Vlijm 8 November 2014 в 09:21

Другие вопросы по тегам:

Похожие вопросы: