Improved algorithms for left factorial residues

04/19/2019 ∙ by Vladica Andrejić, et al. ∙ University of Belgrade Inria 0

We present improved algorithms for computing the left factorial residues !p=0!+1!+...+(p-1)! p. We use these algorithms for the calculation of the residues !p p, for all primes p up to 2^40. Our results confirm that Kurepa's left factorial conjecture is still an open problem, as they show that there are no odd primes p<2^40 such that p divides !p. Additionally, we confirm that there are no socialist primes p with 5<p<2^40.



There are no comments yet.


page 1

page 2

page 3

page 4

Code Repositories


Improved algorithms for left factorial residues

view repo
This week in AI

Get the week's most popular data science and artificial intelligence research sent straight to your inbox every Saturday.

1. Introduction

In 1971, Kurepa [9] introduced the left factorial function for an integer , defined as the sum of factorials . Kurepa conjectured that the greatest common divisor of and is equal to for all integers . Equivalently, the conjecture claims that there are no odd primes such that divides . This problem has been studied extensively and was called Kurepa’s conjecture by the subsequent authors. For a historical background, the reader can consult [1]. The conjecture is also listed in Richard Guy’s classical book [6, Section B44]; as of 2019, it is still an open problem.

In the past, there were several attempts to disprove the conjecture by finding a counterexample. In the most recent search [1], no counterexample was found for any . All such searches are based on calculations of residues for primes . In all previous attempts, the time complexity of algorithms was for a single and for all . We now show that the computational complexity can be significantly improved and we extend the search range up to .

These improvements are based on the simple observation that and can be represented altogether in a matrix factorial form as

Applying [3, Theorem 8] on the matrix factorial , yields an improved algorithm for computing a single remainder in time . In practice, due to the overhead of the FFT-based polynomial multiplication, this method does not significantly outperform the one given in [1] for around . However, the improvement is notable for larger values of . We used this method to verify the individual values obtained by the algorithm we will describe next.

The main method we used in our search is based on the work presented in [4]. The algorithm was originally designed for computing Wilson primes, and is easy to adapt to matrix factorials. As a consequence, the remainders for can be computed altogether in time . However, for large , due to the limited computing resources, we need to run the search on smaller intervals. The time complexity of the method we used to compute the remainders for is

Let us denote the terms we will use in the following section, where some definitions are similar to those that appear in [4, Theorem 2]. Let . For each and we set

Then we introduce


For each prime it follows that is congruent to the -entry of the matrix .

2. Implementation

For large integer arithmetic computations, we used the memory GMP [5] and NTT [8]. The NTT library supports multithreading without an additional memory overhead and performs integer multiplication faster than GMP routines when the operands are sufficiently large. This setup is similar to the solution given in [4]. To generate a list of primes, we used the implementation of the sieve of Eratosthenes provided by the FLINT library [7]. The source code of our implementation is available at

To compute all remainders for primes in an interval , we implemented the following four phases.

2.1. Phase 1: computation of the

This phase consists of two parts. First, we generated a list of primes in , then we computed and stored all using a product tree. The time complexity of this phase is .

2.2. Phase 2: computation of

We computed by using a product tree. The time complexity of this phase is . This phase represents the bottleneck of the proposed algorithm.

It is obvious that this phase will dominate as we proceed with the search. In practice, when we continue the search within the next interval , we can apply additional tricks to reduce the computation time by a constant factor. As we performed the multiplication going from the bottom to the top level of the product tree, once we reached the highest level with all intermediate results less than , we stored them. We further used these saved values to avoid the repetition of the majority of operations we needed to perform without modular reduction. The optimal results were achieved when the stored values were just slightly less than , which additionally required that the tree is partitioned carefully.

Unfortunately, this approach significantly increased space requirements (measured in terabytes). As the data storage solutions are less expensive compared to the cost of RAM or the price per CPU core, we decided to reduce the computation time on account of the increase of the storage space. To reduce the hard disk I/O we used a smaller solid-state drive, where we stored intermediate results. This way the disk I/O did not represent a bottleneck.

As this phase is the most time expensive, the best performance is obtained if the interval is as large as possible, which is limited by the available RAM.

2.3. Phase 3: computation of the

To compute , we also used a product tree. To optimize space usage, we stored only . Additionally, we used the results from this phase to prepare the computation of for the next search interval as described in Phase 2. The time complexity of this phase is .

2.4. Phase 4: computation of the

This phase is similar to Phase 3, with the difference that we performed the computation starting from the top level of the product tree , going down to the level . The only values we had to store during this process belonged to the level we were currently processing and those contained in one level above. The time complexity of this phase is also .

2.5. Verification of the results

To verify a subset of computed values , we used a procedure based on the algorithm described in [3], with the time complexity per prime . The polynomial multiplication is performed by using the NTL library [10].

2.6. Hardware

The computation was performed using a 6-core CPU (i7 6800K). The configuration was equipped with 64GB of RAM and 16TB of disk space. The entire computation took approximately core hours, where about % of the time was spent in Phase 2. For a couple of the last blocks we processed, the time spent in Phase 2 was approaching %.

3. Results

We calculated and stored for all primes less than

. Heuristic considerations suggest that

is a random number modulo

with uniform distribution, so the probability that

has any particular value is approximately , and the sum of reciprocals of the primes diverges. Thus, we might expect that the probability to find a counterexample in an interval is approximately , and the expected number of primes with is approximately [1].

The new search covered the interval , where this heuristic predicts approximately 15% of chances to find a counterexample. Although we only found 24 primes with

in our interval in comparison with the expected value 32, the heuristics give good estimates for higher values of 

. For the expected number of primes in this interval is , which is close to the actual value . Similarly, for , the predicted value  is close to the actual value . The results for are presented in the following table.

Additionally, we have used our new algorithms in a search for socialist primes. The socialist primes are the primes  for which the residues of , , …, modulo are all distinct [11]. Erdős conjectured that any prime is socialist, see  [6, Section F11]. In our previous work [2] we proved that a socialist prime needs to satisfy , and showed there are no socialist primes with . Our new results confirm that there are no primes in the interval such that the remainder satisfies the desired congruence. Consequently, there are no socialist primes with .


  • [1] V. Andrejić and M. Tatarevic, Searching for a counterexample to Kurepa’s conjecture, Math. Comp. 85 (2016), 3061–3068.
  • [2] V. Andrejić and M. Tatarevic, On Distinct residues of factorials, Publ. Inst. Math., Nouv. Sér. 100 (2016), 101–106.
  • [3] A. Bostan, P. Gaudry, and E. Schost, Linear recurrences with polynomial coefficients and application to integer factorization and Cartier-Manin operator, SIAM J. Comput. 36 (2007), 1777–1806.
  • [4] E. Costa, R. Gerbicz, and D. Harvey, A search for Wilson primes, Math. Comp. 83 (2014), 3071–3091.
  • [5] T. Granlund and the GMP development team, GNU MP: The GNU Multiple Precision Arithmetic Library, Version 6.1.2 (2016),
  • [6] R. Guy, Unsolved Problems in Number Theory (3rd edition), Springer-Verlag, 2004.
  • [7] W. Hart, F. Johansson, and S. Pancratz, FLINT: Fast Library for Number Theory, Version 2.5.2 (2015),
  • [8] D. Harvey, NTT: A library for large integer arithmetic, Version 0.1.2 (2012).
  • [9] Đ. Kurepa, On the left factorial function , Math. Balk. 1 (1971), 147–153.
  • [10] V. Shoup, NTL: A Library for doing Number Theory, Version 10.3.0 (2016),
  • [11] T. Trudgian, There are no socialist primes less than , Integers 14 (2014), #A63.