Какой может быть процедура / код для удаления «строкового выражения» из файла с помощью Apache Pig? - PullRequest
0 голосов
/ 11 января 2012
A = load '/home/wrdtest.txt';

B = foreach A generate flatten(TOKENIZE((chararray)$0)) as word;

C = filter B by word != 'the';

D = group C by word;

E = foreach D generate COUNT(C) as count, group as word;

F = order E by count desc;

store F into '/tmp/sample_data20';

Я просто хочу отфильтровать текст. 3-й шаг фильтрует текст и удаляет «из» из текстового файла. Но я хочу удалить из текста набор из 499 слов (стоп-слов). Я пытался использовать '|' (как ИЛИ) как:

C = filter B by word != 'the|and|or'...but it didnt work.

Не могли бы вы предложить это, и могу ли я включить текстовый файл, например (stopwords.txt), чтобы удалить стоп-слова.

Я наивный пользователь Pig

Ответы [ 2 ]

4 голосов
/ 11 января 2012

Что-то вроде удаления стоп-слов достаточно сложно, чтобы его не было во встроенных функциях. Вам нужно написать пользовательскую функцию , что довольно просто сделать.

-- load the data line by line
lines = LOAD 'datafile.txt' USING TextLoader() AS (line:chararray);

-- apply some sort of UDF that returns the exact line without the stop words
nostop = FOREACH lines GENERATE myudfs.removestop(line);

-- store the data out
STORE nonstop INTO 'datafile_nostop.txt';

Подтолкнуть этот список к задачам - это другая история. Если список сравнительно небольшой, порядка тысяч, вы можете вставить стоп-слова в свой код (то есть жестко закодировать список), чтобы он был доступен. В противном случае вы можете использовать распределенный кэш, чтобы вытолкнуть файл.


С учетом предоставленной вами дополнительной информации я могу предложить альтернативный подход. Мой вышеупомянутый подход к использованию UDF все еще действителен.

Этот новый подход подразумевает загрузку другого файла, а затем эффективное анти-объединение для удаления объектов, соответствующих списку. Вам нужно убедиться, что stopwords.txt содержит по одному слову в строке, чтобы это работало. Чтобы выполнить анти-объединение (т. Е. Сохранить те элементы списка, которые не соответствуют другому списку), я сделаю левое внешнее объединение (с использованием реплицируется ), затем отфильтрую где столбец стоп-слов равен нулю (т. е. у него не было совпадающего стоп-слова).

A = load '/home/wrdtest.txt';

-- load the stop words list
SW = load '/home/stopwords.txt' as (stopword:chararray);    

B = foreach A generate flatten(TOKENIZE((chararray)$0)) as word;

-- join the data with a left outer join
-- using replicated should be done with the right relation (SW) is small
SW2 = join B by word LEFT OUTER, SW by stopword USING 'replicated';

-- filter out where the stopword is null, meaning it is not in the stopword list
C = filter SW2 by stopword IS NULL;

-- remove the stopword column that we don't need.
C = foreach C generate word;

D = group C by word;

E = foreach D generate COUNT(C) as count, group as word;

F = order E by count desc;

store F into '/tmp/sample_data20';
2 голосов
/ 25 августа 2013

Я использовал приведенное выше решение Дональда Майнера.

Я изменил отношение о JOIN части как следующее

SW2 = join B by word LEFT, SW by stopword;

и работает для меня.

...