Более быстрый способ перечисления чисел, чем GNU seq?

Я хочу перечислить числа (в диапазоне от 1 до 10 136), но до сих пор большинство инструментов и трюков, которые я пробовал, не работали после 10 9чисел или около того. ...

Вот несколько примеров (с меньшим диапазоном):

Для seq 99999

real    0m0.056s
user    0m0.004s
sys     0m0.051s

Для seq 9999999

real    1m5.550s
user    0m0.156s
sys     0m6.615s

И так далее и тому подобное... Дело в том, что он начинает бороться только после 9-го числа или около того (в данном случае 999999999) и далее.Я подумал о том, чтобы разделить их на меньший диапазон и запустить их параллельно:

cat <(seq 000 999) <(seq 999 1999) <(seq 1999 2999) <(seq 2999 3999) <(seq 3999 4999) <( seq 4999 5999) <(seq 5999 6999) <(seq 6999 7999) <(seq 7999 8999) <(seq 8999 9999) <(seq 9999 10999) <(seq 10999 11999) <(seq 11999 12991) <(seq 13999) <(seq 13999 14999)

real    0m0.258s
user    0m0.008s
sys     0m0.908s

, что значительно медленнее (особенно с большим радиусом действия), чем seq 000 14999

real    0m0.042s
user    0m0.000s
sys     0m0.041s

Я попробовал Perl-скрипт, который нашел на SO:

#!/usr/bin/perl
use strict;
if ( ($#ARGV+1)!=2 ) { print "usage $0  \n"; }
my @r = &bitfizz( $ARGV[0], $ARGV[1] );
for(@r){ print "$_\n"; }
sub bitfizz() {
    $_[0]=join( ",", split(//, $_[0] ) );
    for( my $i=1; $i<=$_[1]; $i+=1 ) { $_=$_."{$_[0]}"; }
    @r=glob( $_ );
}

с perl script.pl "0123456789" 10* Но хотя он казался быстрее, чем seq (при выполнении чего-либо меньшего, чем 10 10), он все еще с трудом и кажется, что для его завершения потребуется целая вечность...

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

РЕДАКТИРОВАТЬ:

@Isaac упомянул в своем ответе (и в комментарии) что-то, что могло быработать, и хотя оно работает через 10 10намного быстрее, чем что-либо еще уже упоминалось, он по-прежнему борется за любой диапазон больше 10 10(и, соответственно, 10 136).

Стоит упомянуть, так как это было упомянуто как возможный дубликат этого сообщения (что технически им не является).

Как выполнить нумерацию от 0 до 10 136быстрее, чем GNU seq?

0
15.06.2020, 16:08
1 ответ

I want to enumerate numbers (between 1 to 10^136 range)

и ответы, которые вы уже получили, должны объяснить вам, почему вы этого не сделаете.

Или, да, можно перечислить тогда:

#!/usr/bin/perl
use bigint;
for (1..1e136) { print $_. ", "}

но это займет очень много времени. Как в... намного дольше, чем вы можете рассчитывать прожить. Давайте повеселимся с seq, не так ли?

j=9 TIMEFORMAT='%lR';  \
for i in `seq 1 9`; do 
    j=$(( $j * 10 + 9));
    echo -n "$i digits: ";
    time seq $j > /dev/null; 
done

Я понял

1 digits: 0m0,002s
2 digits: 0m0,002s
3 digits: 0m0,001s
4 digits: 0m0,002s
5 digits: 0m0,014s
6 digits: 0m0,126s
7 digits: 0m1,261s
8 digits: 0m12,631s
9 digits: 2m9,607s

Как вы можете видеть, время запуска доминирует до 9999 включительно, но затем время увеличивается примерно в 10 раз для каждой цифры ---, которую вы полностью ожидаете, поскольку вам нужно обработать в 10 раз больше чисел. И так будет дальше...

  8 digits:~   0.2 minutes
  9 digits:~   2   minutes
 10 digits:~  20   minutes
 11 digits:~ 120   minutes (2 hours)
 36 digits:~ 2e25  hours   (> 3,500 years)
136 digits:~ 2e125 --- never mind.

Это намного больше, чем ваша продолжительность жизни в состоянии покоя. И если вы найдете способ сделать это в 100 раз быстрее (! ), вы все равно будете ждать 3,5 года для 1e36 ---, не говоря уже о цифрах 1e136. Это просто не устойчиво. (Об этом говорили все остальные, но, может быть, это поможет вам понять.)

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

3
18.03.2021, 23:27

Теги

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