Как я могу разделить текст на основе каждого n-го слова? - PullRequest
2 голосов
/ 12 апреля 2020

Я пытаюсь разделить текстовый файл для каждого 1000-го слова.

awk -v RS='[[:space:]]+' 'END{print NR+0}' filename

с помощью awk Я могу посчитать слова в файле, но не знаю, как его разбить.

окончательный вывод = имя файла (1) .txt, имя файла (2) .txt

Ответы [ 3 ]

0 голосов
/ 12 апреля 2020

Вы можете сделать это с awk без особых проблем. Это помогает избавиться от беспорядка, если вы напишите функцию, которая фактически обрабатывает вывод слов из массива в ваш файл. Держите счетчик для нумерации имен выходных файлов, например, wordsfile_1 (первые 1000 слов), wordsfile_2 (следующие 1000 слов) и так далее. Тогда нужно просто отслеживать, сколько слов вы добавляете в ваш массив, и вызывать функцию вывода, когда вы нажимаете 1000 слов. Затем удалите массив, чтобы он был готов содержать следующие 1000 слов, сбросьте счетчик слов и продолжайте.

Например, вы можете сделать что-то вроде:

awk '
    function writefile() {
        fname="wordsfile_" ++c + 0
        for (j=1; j<=n; j++)
            print a[j] > fname
        delete a
        n = 0
    }
    {
        for (i=1; i<=NF; i++) {
            a[++n] = $i
            if (n == 1000)
                writefile()
        }
    }
END {
    writefile()
}' input_file

function writefile() обрабатывает запись вывода в ваши файлы 1000 слов, удаление массива и сброс счетчика n. Правило END просто вызывает функцию еще раз, чтобы вывести любые слова, собранные с момента последнего вывода.

Дайте мне знать, если у вас есть дополнительные вопросы.

0 голосов
/ 13 апреля 2020
#!/bin/bash
for FILE in *.txt
do
#FILE="FILENAME.txt" 
read -p "HOW MANY WORDS SHOULD BE IN YOUR FILES? (~ APPROXIMATE) " BUFFER
#BUFFER=1000 # APPROXIMATE NUMBER OF WORDS IN A FILE 

NW=$(wc -w $FILE | awk '{print $1}') #NW=NUMBER OF WORDS IN YOUR FILE

if [[ $NW -gt $BUFFER ]]
then

LINENUMBER=$(wc -l $FILE | awk '{print $1}')
WCOUNT=0
FL=1 #FIRST LINE NUMBER OF EVERY NEW FILE
FN=1 #FILE NUMBER

for j in $(eval echo "{1..$LINENUMBER}")
do
    INC=$(sed -n "${j}p" $FILE | wc -w)
    WCOUNT=$(( WCOUNT + INC ))
    if [[ $WCOUNT -gt $BUFFER ]];
    then
        sed -n "${FL},${j}p" $FILE >  ${FILE%%.*}_${FN}.txt
        FL=$(( j + 1))
        (( FN++ ))
        WCOUNT=0
    fi
done
sed -n "${FL},\$p" $FILE >  ${FILE%%.*}_${FN}.txt
fi 
done

Я нашел другое решение, оно генерирует файлы, содержащие примерно 1000 слов в каждом.

0 голосов
/ 12 апреля 2020

Это совершенно больное решение должно работать для файлов, которые содержат менее 10000 слов:

. <(echo -e 'uno due tre\nquattro\ncinque sei sette otto\nnove dieci undici dodici tredici' | sed -zE '
s/^/\x0/
:a
y/012345678/123456789/
s/\x0(([^ \n]+[ \n]+){4})/cat > file0 <<EOF\n\1\nEOF\n\x0/
ta
s/\x0(.*)/cat > file0 <<EOF\n\1\nEOF\n\x0/
s/\n+/\n/g')

По сути, оно перемежает некоторый код в точках, где разбиения должны происходить таким образом, что исходящий файл скрипт bash, представляющий собой последовательность команд cat, которые читают из heredocument и записывают в файл (допускается максимум 10 файлов!). Этот сценарий получен (. file просто source file, просто уродливее). Вы можете увидеть скрипт, удалив начальный . <( и завершающий ).

Приятно то, что он разбивает большой файл в середине строк, если это необходимо, без изменения строк, где нет разделения происходит.

Самое уродливое то, что он нумерует файлы в обратном порядке.

Ограничение количества слов связано с тем, что я применяю только одно-ди git дополнение к именам файлов; его можно удалить, внедрив дополнение аналогично тому, как это сделано здесь или здесь .

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...