Поиск трех слов подряд

Я нашел вкладыш AWK 1, и в нем был баг, но я его исправил. Я также добавил PetaBytes после TeraBytes.

FILE_SIZE=234234 # FILESIZE IN BYTES
FILE_SIZE=$(echo "${FILE_SIZE}" | awk '{ split( "B KB MB GB TB PB", v ); s=1; while( $1>1024 ){ $1/=1024; s++ } printf "%.2f %s", $1, v[s] }')

Учитывая, что stat есть не в каждой системе, почти всегда можно использовать решение AWK. Пример; Raspberry Pi не имеет stat , но имеет awk .

4
28.08.2019, 09:39
2 ответа

Следующая программа awkсохраняет подсчет того, сколько раз встречается каждый набор из трех последовательных слов (после удаления знаков пунктуации ), и печатает подсчеты и набор слов в конце, если подсчет больше 1:

{
        gsub("[[:punct:]]", "")

        for (i = 3; i <= NF; ++i)
                w[$(i-2),$(i-1),$i]++
}
END {
        for (key in w) {
                count = w[key]
                if (count > 1) {
                        gsub(SUBSEP," ",key)
                        print count, key
                }
        }
}

Учитывая текст в вашем вопросе, получается

2 Search Inside Yourself
2 Cultivate The Three
2 The Three Essential
2 Joy on Demand
2 Recognize and Cultivate
2 Three Essential Virtues
2 and Cultivate The
2 The Ideal Team
3 Ideal Team Player

Как видите, это может быть не так уж полезно.

Вместо этого мы можем собрать ту же информацию о счете, а затем выполнить второй проход по файлу, печатая каждую строку, содержащую тройку слов с числом больше единицы:

NR == FNR {
        gsub("[[:punct:]]", "")

        for (i = 3; i <= NF; ++i)
                w[$(i-2),$(i-1),$i]++

        next
}

{
        orig = $0
        gsub("[[:punct:]]", "")

        for (i = 3; i <= NF; ++i)
                if (w[$(i-2),$(i-1),$i] > 1) {
                        print orig
                        next
                }
}

Проверка вашего файла:

$ cat file
The Ideal Team Player
The Ideal Team Player: How to Recognize and Cultivate The Three Essential Virtues
Ideal Team Player: Recognize and Cultivate The Three Essential Virtues

Joy on Demand: The Art of Discovering the Happiness Within
Crucial Conversations Tools for Talking When Stakes Are High
Joy on Demand

Search Inside Yourself: The Unexpected Path to Achieving Success, Happiness
Search Inside Yourself
$ awk -f script.awk file file
The Ideal Team Player
The Ideal Team Player: How to Recognize and Cultivate The Three Essential Virtues
Ideal Team Player: Recognize and Cultivate The Three Essential Virtues
Joy on Demand: The Art of Discovering the Happiness Within
Joy on Demand
Search Inside Yourself: The Unexpected Path to Achieving Success, Happiness
Search Inside Yourself

Предупреждение :Этой awkпрограмме требуется достаточно памяти, чтобы сохранить текст вашего файла примерно в три раза, и она может найти дубликаты в общих фразах, даже если записи на самом деле не дублируются (, например. «Как готовить» может быть частью названий нескольких книг ).

7
27.01.2020, 20:48

ИМО, эту задачу лучше решать, используя пересечения наборов слов, а не искать 3 последовательных слова.

Соответственно, следующий perl-скрипт не ищет 3 последовательных слова. Вместо этого он сначала считывает весь ввод (со стандартного ввода и/или одного или нескольких файлов )и (с помощью модуля Set ::Tiny )создает набор слов для каждой строки ввода.

Затем он обрабатывает ввод второй раз и (для каждой строки )выводит все строки, прочитанные при первом проходе, которые имеют точные дубликаты или где пересечение наборов имеет 3 или более элемента .

Он использует хеш-массив с именем %setsдля хранения наборов слов для каждого заголовка, а другой хэш с именем %titlesдля подсчета количества просмотров каждого заголовка -он используется на этапе вывода для убедитесь, что он никогда не печатает заголовок чаще, чем он был замечен во входных данных.

Короче говоря, он печатает повторяющиеся строки и похожие строки (т. е. те, в которых есть как минимум 3 одинаковых слова )рядом друг с другом -3 слова не обязательно должны быть последовательными.

Скрипт игнорирует несколько очень распространенных маленьких слов при построении наборов, но это можно отключить, закомментировав или удалив строку с комментарием OPTIONAL.... Или вы можете отредактировать общий список слов в соответствии с вашими потребностями.

Стоит отметить, что в список маленьких слов в скрипте входит слово by. Вы можете удалить его из списка, если хотите, но причина, по которой он существует, заключается в том, чтобы предотвратить сопоставление скрипта на byплюс любые два других слова -, например. Aardvark Taxidermy for Personal Wealth by Peter Smithбудет соответствоватьThe Wealth of Nations by Adam Smith(совпадениям на by, WealthиSmith).Первая книга (Надеюсь, )вообще -не существует, но если бы она и существовала, то она никак не была бы связана с текстом по экономике.

Примечание. :этот скрипт сохраняет весь ввод и связанные с ним наборы слов для каждой строки ввода в памяти. Это вряд ли будет проблемой для современных систем с несколькими гигабайтами свободной оперативной памяти, если входные данные не очень велики.

Note2:Set::Tinyупакован для Debian как libset-tiny-perl. Он может быть доступен предварительно упакованным -и для других дистрибутивов. В противном случае вы можете получить его по ссылке CPAN выше.

#!/usr/bin/perl -w

use strict;
use Set::Tiny;

# a partial list of common articles, prepositions and small words joined into
# a regex.
my $sw = join("|", qw(
  a about after against all among an and around as at be before between both
  but by can do down during first for from go have he her him how
  I if in into is it its last like me my new of off old
  on or out over she so such that the their there they this through to
  too under up we what when where with without you your)
);

my %sets=();    # word sets for each title.
my %titles=();  # count of how many times we see the same title.

while(<>) {
  chomp;
  # take a copy of the original input line, so we can use it as
  # a key for the hashes later.
  my $orig = $_;

  # "simplify" the input line
  s/[[:punct:]]//g;  #/ strip punctuation characters
  s/^\s*|\s*$//g;    #/ strip leading and trailing spaces
  $_=lc;             #/ lowercase everything, case is not important.
  s/\b($sw)\b//iog;  #/ optional. strip small words
  next if (/^$/);

  $sets{$orig} = Set::Tiny->new(split);
  $titles{$orig}++;
};

my @keys = (sort keys %sets);

foreach my $title (@keys) {
  next unless ($titles{$title} > 0);

  # if we have any exact dupes, print them. and make sure they won't
  # be printed again.
  if ($titles{$title} > 1) {
    print "$title\n" x $titles{$title};
    $titles{$title}  = 0;
  };

  foreach my $key (@keys) {
    next unless ($titles{$key} > 0);
    next if ($key eq $title);

    my $intersect = $sets{$key}->intersection($sets{$title});
    my $k=scalar keys %{ $intersect };

    #print STDERR "====>$k(". join(",",sort keys %{ $intersect }). "):$title:$key\n" if ($k > 1);

    if ($k >= 3) {
      print "$title\n" if ($titles{$title} > 0);
      print "$key\n" x $titles{$key};
      $titles{$key}   = 0;
      $titles{$title} = 0;
    };
  };
};

Сохранить как, например. blueray.plи сделайте его исполняемым с помощью chmod +x.

Учитывая новый входной образец, он выдает следующий результат:

$./blueray.pl TestData.txt 
7L: The Seven Levels of Communication
The Seven Levels of Communication: Go From Relationships to Referrals by Michael J. Maher
A History of Money and Banking in the United States: The Colonial Era to World War II
The History of Banking: The History of Banking and How the World of Finance Became What it is Today
America's Bank: The Epic Struggle to Create the Federal Reserve
America's Money Machine: The Story of the Federal Reserve
Freakonomics: A Rogue Economist
Freakonomics: A Rogue Economist Explores the Hidden
Freakonomics: A Rogue Economist Explores the Hidden
Freakonomics: A Rogue Economist Explores the Hidden Side of Everything by Steven Levitt
Money Master the Game by Tony Robbinson
Money Master the Game by Tony Robbinson
Money Master the Game by Tony Robbinson
The Federal Reserve and its Founders: Money, Politics, and Power
The Power and Independence of the Federal Reserve
Venture Deals by Brad Feld
Venture Deals by Brad Feld & Jason Mendelson
Zen and the Art of Motorcycle Maintenance: An Inquiry into Values
Zen and the Art of Motorcycle Maintenance: An Inquiry into Values

Это не совсем то же самое, что вывод вашего примера. Поскольку он проверяет наличие общих слов в заголовках, игнорируя их точный порядок, с большей вероятностью будут найдены ложные срабатывания и менее вероятно, что будут пропущены совпадения, которых не должно быть (ложноотрицательные ).

Если вы хотите поэкспериментировать с этим или просто посмотреть, какие слова соответствуют (или почти соответствуют ), вы можете раскомментировать строку #print STDERR

3
27.01.2020, 20:48

Теги

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