I am trying to write a program to find the nth prime. To do this I use the limit given by the prime number theorem:
p(n) < n(ln(n) + ln(ln(n))
to calculate an upper bound for the nth prime number, use constant generics to create an array of that length and then perform a sieve of Eratosthenes to find all primes in that array. However, I have run into the issue that my current code will not compile due to the line:
const N_PRIME: i32 = 10_001;
// ceil use instead of floor to remove possibility of floating point error causing issue with bound
// 1 added to account for array indices starting from 0
const UP_TO: i32 = {let np = N_PRIME as f64; (np * (np.ln() + np.ln().ln())).ceil() as i32 + 1};
with the error message
const UP_TO: i32 = {let np = N_PRIME as f64; (np * (np.ln() + np.ln().ln())).ceil() as i32 + 1};
| ^^^^
|
= note: calls in constants are limited to constant functions, tuple structs and tuple variants
naturally I could simply calculate UP_TO
and hardcode it, or I could rewrite the code to use vectors. However, the former approach is more clunky and the latter would be slightly slower so a workaround would be preferable. Can anyone think of a way to get the needed value into the UP_TO
constant?
Thanks
Edit: Code suggested by pigionhands (as I understand it), this code results in the same error:
const N_PRIME: i32 = 10_001;
fn up_to<const N_PRIME: i32>() -> usize {
let np = N_PRIME as f64;
(np * (np.ln() + np.ln().ln())).ceil() as usize + 1
}
fn main() {
println!("{}", UP_TO);
let test_arr = [0; up_to::<N_PRIME>()];
}