generate_psp_from_prime_factors_db.pl 1.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960
  1. #!/usr/bin/perl
  2. # Generate Fermat pseudoprimes of the form: p*((p-1)*k + 1), for some small constant k.
  3. use 5.020;
  4. use strict;
  5. use warnings;
  6. use Math::GMPz;
  7. use ntheory qw(:all);
  8. use Math::Prime::Util::GMP;
  9. use experimental qw(signatures);
  10. eval { require GDBM_File };
  11. my $cache_db = "cache/factors.db";
  12. dbmopen(my %db, $cache_db, 0444)
  13. or die "Can't create/access database <<$cache_db>>: $!";
  14. my %table;
  15. #my $CONSTANT_K = 2;
  16. my $CONSTANT_K = 3;
  17. #my $CONSTANT_K = 4;
  18. #my $CONSTANT_K = 20;
  19. #my $CONSTANT_K = 204;
  20. #my $CONSTANT_K = 548;
  21. my $MIN_P = sqrtint(divint(powint(2, 64), $CONSTANT_K));
  22. open my $fh, '>>', 'special_fermat_psp.txt';
  23. say ":: Generating with k = $CONSTANT_K... Please wait...";
  24. my %seen_p;
  25. while (my ($key, $value) = each %db) {
  26. my @f = split(' ', $value);
  27. next if $f[-1] < $MIN_P;
  28. foreach my $p (@f) {
  29. if ($p > $MIN_P) {
  30. next if $seen_p{$p}++;
  31. my $t = Math::Prime::Util::mulint($p, addint(mulint($CONSTANT_K, subint($p, 1)), 1));
  32. if (Math::Prime::Util::GMP::is_pseudoprime($t, 2)) {
  33. say $fh $t;
  34. }
  35. }
  36. }
  37. }
  38. say ":: Done...";
  39. close $fh;
  40. dbmclose(%db);