2015-11-28 2 views
2

Мне нужно обработать большое количество файлов txt в папке с использованием сценариев bash. Каждый файл содержит миллион строк и они отформатированы, как это:Обработать большой объем данных с помощью bash

Файл № 1:

en ample_1 200 
it example_3 24 
ar example_5 500 
fr.b example_4 570 
fr.c example_2 39 
en.n bample_6 10 

Файл № 2:

de example_3 4 
uk.n example_5 50 
de.n example_4 70 
uk example_2 9 
en ample_1 79 
en.n bample_6 1 

...

Я получил фильтр «en» или «en.n», обнаружив повторяющиеся вхождения во втором столбце, суммируйте третий colum и получите отсортированный файл следующим образом:

en ample_1 279 
en.n bample_6 11 

Вот мой сценарий:

#! /bin/bash 
clear 
BASEPATH=<base_path> 
FILES=<folder_with_files> 
TEMP_UNZIPPED="tmp" 
FINAL_RES="pg-1" 
#iterate each file in folder and apply grep 
INDEX=0 
DATE=$(date "+DATE: %d/%m/%y - TIME: %H:%M:%S") 
echo "$DATE" > log 
for i in ${BASEPATH}${FILES} 
do 
FILENAME="${i%.*}" 
if [ $INDEX = 0 ]; then 
    VAR=$(gunzip $i) 
    #-e -> multiple condition; -w exact word; -r grep recursively; -h remove file path 
    FILTER_EN=$(grep -e '^en.n\|^en ' $FILENAME > $FINAL_RES) 
    INDEX=1 
    #remove file to free space 
    rm $FILENAME 
else 
    VAR=$(gunzip $i) 
    FILTER_EN=$(grep -e '^en.n\|^en ' $FILENAME > $TEMP_UNZIPPED) 
    cat $TEMP_UNZIPPED >> $FINAL_RES 
    #AWK BLOCK 
    #create array a indexed with page title and adding frequency parameter as value. 
    #eg. a['ciao']=2 -> the second time I find "ciao", I sum previous value 2 with the new. This is why i use "+=" operator 
    #for each element in array I print i=page_title and array content such as frequency 
    PARSING=$(awk '{ page_title=$1" "$2; 
        frequency=$3; 
        array[page_title]+=frequency 
        }END{ 
        for (i in array){ 
         print i,array[i] | "sort -k2,2" 
        } 
        }' $FINAL_RES) 

    echo "$PARSING" > $FINAL_RES 
    #END AWK BLOCK 
    rm $FILENAME 
    rm $TEMP_UNZIPPED 
fi 
done 
mv $FINAL_RES $BASEPATH/06/01/ 
DATE=$(date "+DATE: %d/%m/%y - TIME: %H:%M:%S") 
echo "$DATE" >> log 

Все работает, но это займет много много времени, чтобы выполнить. Кто-нибудь знает, как получить тот же результат, с меньшим количеством временных и меньших строк кода?

+0

'bash' есть * нет * для обработки * большой * количество данных. Если данные достаточно велики, стоит потратить время на разработку более эффективной программы (возможно, на компилированном языке). Но * вам нужно измерить баланс и оценить время. Ожидание 5 минут может быть в порядке (но ждать 5 дней, чтобы ваш скрипт bash заканчивался, оправдывает расходы на 2 часа на кодирование программы на C или Ocaml) –

+0

Кроме того, насколько велики фактические данные (мегабайты или терабайты), как часто это изменение, и как долго вы дождались завершения вашего скрипта? И каковы ваши навыки программирования? –

ответ

6

Оболочка UNIX - это среда, из которой можно манипулировать файлами, процессами и последовательными вызовами инструментов. Инструмент UNIX, которые оболочка требует, чтобы манипулировать текст является AWK так просто использовать:

$ awk '$1~/^en(\.n)?$/{tot[$1" "$2]+=$3} END{for (key in tot) print key, tot[key]}' file | sort 
en ample_1 279 
en.n bample_6 11 

Ваш сценарий слишком много вопросов, чтобы прокомментировать что указывает вы новичок в программировании оболочки - получить книги Bash Shell Scripting Рецепты Крис Джонсон и эффективное программирование Awk, 4-е издание, Арнольд Робинс.

+0

Спасибо за ваш ответ Эд. Да, я новичок в программировании оболочки. О каких проблемах вы говорите? Я должен обрабатывать много файлов в одной папке, кажется, что ваш скрипт способен обрабатывать только одно из них. Я ошибаюсь? –

+0

Прошу прощения, у меня есть слишком много проблем с вашим скриптом, чтобы я мог их перечислить. Если вы хотите, чтобы скрипт обрабатывал более одного файла, просто перечислите файлы в командной строке, например 'awk 'script' file1 file2 ... fileN', и, очевидно, вы можете использовать' file * 'или любую конструкцию, в которой вы хотите, чтобы оболочка развернуть список имен файлов –

+1

Хорошо, спасибо. Я получу книгу, которую вы мне предложили! –

Смежные вопросы