-
Notifications
You must be signed in to change notification settings - Fork 0
/
hcn.pl
85 lines (65 loc) · 2.16 KB
/
hcn.pl
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
#!/usr/bin/perl
# Daniel "Trizen" Șuteu
# Date: 27 June 2019
# https://github.com/trizen
# Print the n-th highly composite number, using data generated by Achim Flammenkamp.
# See also:
# https://oeis.org/A321995 -- Indices of highly composite numbers A002182 which are between a twin prime pair.
# https://oeis.org/A108951 -- Completely multiplicative with a(p) = p# for prime p, where x# is the primorial A034386(x).
# https://oeis.org/A002182 -- Highly composite numbers, definition (1): where d(n), the number of divisors of n (A000005), increases to a record.
use 5.020;
use strict;
use warnings;
use Math::GMPz;
use ntheory qw(:all);
use POSIX qw(ULONG_MAX);
use IO::Uncompress::Bunzip2;
use experimental qw(signatures);
local $| = 1;
prime_precalc(1e7);
# "HCN.bz2" was generated by Achim Flammenkamp, and is available at:
# http://wwwhomes.uni-bielefeld.de/achim/HCN.bz2
my $z = IO::Uncompress::Bunzip2->new("HCN.bz2");
my $from = shift(@ARGV) // die "usage: perl $0 [from] [to=from]\n";
my $to = shift(@ARGV) // $from;
if ($from < 0) {
die "error: $from must be a positive integer\n";
}
if ($to < $from) {
die "error: $to must be >= $from\n";
}
my $tmp = Math::GMPz->new(1);
while (defined(my $line = $z->getline())) {
if ($. < $from) {
next;
}
my @fields = split(' ', $line);
my $omega = shift(@fields);
my @primes = (($omega > 0) ? @{primes(nth_prime($omega))} : ());
my $prod = Math::GMPz->new(1);
while (@primes) {
my $k = shift(@fields) // die "unexpected error: $line\n";
my $e = 1;
if ($k =~ /^(\d+)\^(\d+)\z/) {
$k = $1;
$e = $2;
}
for (1 .. $e) {
my $p = shift(@primes);
if ($k == 1) {
Math::GMPz::Rmpz_mul_ui($prod, $prod, $p);
}
elsif ($p**$k < ULONG_MAX) {
Math::GMPz::Rmpz_mul_ui($prod, $prod, powint($p, $k));
}
else {
Math::GMPz::Rmpz_ui_pow_ui($tmp, $p, $k);
Math::GMPz::Rmpz_mul($prod, $prod, $tmp);
}
}
}
if ($. >= $from) {
say "$. $prod";
last if $. >= $to;
}
}