У меня есть файл, который содержит несколько тысяч чисел, каждое в своей строке:
34 42 11 6 2 99 ...
Я хочу написать скрипт, который будет печатать сумму всех чисел в файле. У меня есть решение, но оно не очень эффективно. (Запуск занимает несколько минут.) Я ищу более эффективное решение. Есть предложения?
Вот решение с использованием python с выражением генератора. Протестировано с миллионами чисел на моем старом ноутбуке
time python -c "import sys; print sum((float(l) for l in sys.stdin))" < file real 0m0.619s user 0m0.512s sys 0m0.028s
Просто для удовольствия, давайте сделаем это с PDL , математическим движком Perl!
perl -MPDL -E 'say rcols(shift)->sum' datafile
rcols считывает столбцы в матрицу (в данном случае 1D), а sum (неожиданность) суммирует все элементы матрицы.
rcols
sum
cat nums | perl -ne '$sum += $_ } { print $sum'
(аналогично ответу Брайана Д. Фоя, без 'END')
Более кратко:
# Ruby ruby -e 'puts open("random_numbers").map(&:to_i).reduce(:+)' # Python python -c 'print(sum(int(l) for l in open("random_numbers")))'
$ perl -MList::Util=sum -le 'print sum <>' nums.txt
sed ':a;N;s/\n/+/;ta' file|bc
say sum lines
~$ perl6 -e '.say for 0..1000000' > test.in ~$ perl6 -e 'say sum lines' < test.in 500000500000
с рубином:
ruby -e "File.read('file.txt').split.inject(0){|mem, obj| mem += obj.to_f}"
Я не проверял это, но оно должно работать:
cat f | tr "\n" "+" | sed 's/+$/\n/' | bc
Возможно, вам придется добавить "\ n" в строку перед bc (как через echo), если bc не обрабатывает EOF и EOL ...
еще один для развлечения
sum=0;for i in $(cat file);do sum=$((sum+$i));done;echo $sum
или только другой удар
s=0;while read l; do s=$((s+$l));done<file;echo $s
Но решение awk, вероятно, лучше, поскольку оно наиболее компактно.