Оптимальный способ передачи множества файлов в Gnu Parallel - PullRequest
0 голосов
/ 02 октября 2018

Мне нужна помощь в оптимизации параллельной работы GNU, когда входные данные содержатся во многих файлах, которые должны быть объединены вместе и переданы в несколько различных команд, каждая из которых должна выполняться параллельно.

Я анализирую данные из архива, содержимое которого содержится во многих файлах.Цель состоит в том, чтобы разбить различные типы данных на файлы по типу для всего архива.Чтобы добиться этого, я объединяю файлы вместе и передаю их в каждую команду синтаксического анализа.Парсер принимает данные на stdin и принимает в качестве аргумента тип данных для анализа (например, 'parser type1' для анализа данных типа 1 и т. Д.)

На данный момент у меня есть что-то вроде этого:

parallel --xapply ::: \ 
   'cat datadir/*.dat | parser type1 > type1.txt' \ 
   'cat datadir/*.dat | parser type2 > type2.txt' \ 
   'cat datadir/*.dat | parser type3 > type3.txt'

Но это требует объединения данных несколько раз, что является медленным и кажется ненужным дорогостоящим.Кроме того, я понимаю, что существует ограничение пропускной способности канала.Есть ли лучший способ добиться этого?

1 Ответ

0 голосов
/ 03 октября 2018

Это немного сложно, но позволяет избежать чтения datadir/*.dat более одного раза, вместо временных файлов используются пятерки.

# Example parser
parser() { cat | grep "$@"; }
# Make function visible to GNU Parallel
export -f parser

types="type1 type2 type3"
# Create fifos: myfifo-type1 myfifo-type2 myfifo-type3
parallel mkfifo myfifo-{} ::: $types
# Send datadir/*.dat to 'parser type1', 'parser type2', 'parser type3'
# send output to myfifo-type1 myfifo-type2 myfifo-type3
cat datadir/*.dat |
  parallel -j0 --pipe --tee parser {} '>' myfifo-{} ::: $types &
# Read from the fifos
parallel --xapply echo :::: myfifo*
rm myfifo*

Немного неясно, какую команду вы хотите в финале --xapply.Возможно, вам нужно просто отправить один и тот же ввод на parser с другими параметрами:

cat datadir/*.dat |
  parallel -j0 --pipe --tee parser {} '>' output-{} ::: $types

, что намного проще, чем настройка mkfifo выше.

Pipes / fifosочень быстрые (> 2 ГБ / с) и нет ограничений на количество данных, которые вы можете передать через них.Они избегают попадания данных на диск.

...