Как получить числа из файла и вычислить с помощью сценария оболочки [закрыто]

У меня есть файл с именем numbers.txt. Они содержат такие числа, как это

1568
14578
2365
41655
9965
...
...

. Мне нужно вычислить сумму этих чисел. Как я могу это сделать с помощью сценария оболочки ??

1
задан 8 July 2015 в 13:04

6 ответов

Используя awk

awk -F' ' '{for (i=1;i<=NF;i++) {sum+=$i;} print sum}' <your_file> | tail -1

, Если существует другой разделитель, чем space, используйте -F'<your_delimiter>', например: -F':'

<час>

Используя numsum (sudo apt-get install num-utils)

numsum -r <your_file> | numsum 

, Если существует другой разделитель, чем space, используйте -s <your_delimiter>, например: -s ':'

<час>

Пример

% awk '{for (i=1;i<=NF;i++) {sum+=$i;} print sum}' foo         
70131
106625020

% awk '{for (i=1;i<=NF;i++) {sum+=$i;} print sum}' foo | tail -1
106625020

% numsum -r foo | numsum
106625020

% awk '{for (i=1;i<=NF;i++) {sum+=$i;} print sum}' bar | tail -1
70131

% numsum -r foo | numsum
70131

% cat foo
1568 14578 2365 41655 9965
7673 8273923 98273293

% cat bar
1568
14578
2365
41655
9965
1
ответ дан 3 December 2019 в 06:22

Для разделенных от строки входных файлов следующий awk код работает хорошо:

awk '{s+=$1} END {print s}' numbers.txt

сообщается, что с некоторыми версиями awk могут быть некоторые неожиданные поведения, если сумма будет больше чем 2 147 483 647.

Относятся к это ТАК ответ и его комментарии.

1
ответ дан 3 December 2019 в 06:22

Используя до н.э:

paste -sd"+" file | bc
0
ответ дан 3 December 2019 в 06:22

Если Ваш файл огромен (например, seq 1 100000000 > numbers.txt), традиционные инструменты начинают разваливаться.

  • awk '{s+=$1} END {print s} берет 34, но "0%" RAM (не уверенный, если это точно),
  • perl -nle '$sum += $_ } END { print $sum' numbers.txt взял 27 и крошечную сумму RAM.
  • Python Jacob берет 47 и 6 ГБ RAM (и 23, когда выполнено с pypy, та же RAM)
  • numsum было ужасно; это взяло 9m43 s и 14 ГБ RAM для предоставления экспоненциального числа (другие ответили с полными длинными целыми),
  • Чистый Bash взял бы forever-and-a-day к для цикла по ним так, я не делаю попытку его

Альтернатива, которую я предлагаю ответу, который может добавить сто миллионов целые числа через 6,4 секунд...

... Но это записано в C. Легкий C. Никакие странные требования для создания, или градус не должны были понимать это, но действительно необходимо скомпилировать его, и имя файла является hardcoded в него (который Вы могли зафиксировать)...

#include <stdio.h>

int main(void) {
    FILE *fp;

    char line[100];
    unsigned long int total = 0;

    fp = fopen("numbers.txt", "r");

    while (fgets(line, 100, fp) != NULL) {
        total += atoi(line);
    }
    fclose(fp);

    printf("%li\n", total);

    return 0;
}

Сохраните это как что-то как add.c, выполненный make add и затем ./add работать.

5
ответ дан 3 December 2019 в 06:22

Используя perl и принятие разделителя пространства:

perl -MList::Util=sum -ne 'print sum(split())."\n"' numbers.txt

Для a , использование разделителя:

perl -MList::Util=sum -ne 'print sum(split(/,/))."\n"' numbers.txt

Но предпочтите эту команду, если они - каждый на своей собственной строке:

perl -nle '$sum += $_ } END { print $sum'
1
ответ дан 3 December 2019 в 06:22

В Python:

python -c "print(sum(int(n) for n in open('f').read().split()))"

где f является файлом (+path) между (единственными) кавычками, например:

python -c "print(sum(int(n) for n in open('/home/jacob/Bureaublad/file.txt').read().split()))"

Разделитель может быть изменен в разделе .split(). Если, например, разделитель запятая, набор: .split(','). По умолчанию числа разделяются обоими \n и " ".

Объяснение:

open('f').read().split()

читает файл, разделяет его на числа (как строки)

(int(n) for n in...

преобразовывает строки в числа

print(sum(...

наконец, суммирует найденные числа и печатает результат

Тест

Результат на файле:

1 2 3 4 5 200 2345

2560

Но также и; с тех пор split() разделения на \n также:

1 
2
3
4
5
200
2345

2560

Править

Хотя конкуренция с ответом Oli на скорости и ресурсах была бы фатальной ошибкой, ЕСЛИ БЫ файл будет огромен, по крайней мере, на использовании ресурсов, сценарий ниже предложил бы важное улучшение. Хотя сценарий быстрее затем один - лайнер в моем исходном ответе, самое большое улучшение находится на использовании памяти.

#!/usr/bin/env python3
import sys
total = 0
with open(sys.argv[1]) as lines:
    for l in lines:
        total = total+int(l)
print(total)

Сохраните его как addnumbers.py, выполните его с текстовым файлом как аргумент:

python3 <script> <file>
0
ответ дан 3 December 2019 в 06:22

Другие вопросы по тегам:

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