Cod sursa(job #232232)
#include <iostream>
#include <fstream>
#include <cmath>
using namespace std;
bool isPrime(int x)
{
if (x < 2)
return false;
if (x == 2)
return true;
if (x % 2 == 0)
return false;
int limit = sqrt(x);
for (int i = 3; i <= limit; i+=2) {
if (x % i == 0)
return false;
}
return true;
}
long findPrimePos(int *v, long size, long startIndex)
{
while (startIndex < size && !isPrime(v[startIndex]))
startIndex++;
return startIndex;
}
void outputSol(long long sol)
{
ofstream out("kprime.out");
out << sol << endl;
out.close();
}
int main()
{
ifstream in("kprime.in");
long n, k;
in >> n;
in >> k;
int *v = new int[n];
for (long i = 0; i < n; i++)
in >> v[i];
in.close();
if (k <= 0) {
outputSol(0);
return 0;
}
long *jmp = new long[n];
long leftPrime = findPrimePos(v, n, 0);
if (leftPrime == n) {
// no prime numbers in input
outputSol(0);
return 0;
}
// find all primes and mark intervals in jmp[] vector
long crt = leftPrime;
while (crt < n) {
long next = findPrimePos(v, n, crt + 1);
jmp[crt] = next - crt;
crt = next;
}
// non-primes to the left + 1
long leftCount = leftPrime + 1;
long rightPrime = leftPrime;
// non-primes to the right + 1
long rightCount = jmp[rightPrime];
// primes in interval [left, right]
long primesInSeq = 1;
// put k prime numbers between [left, right]
while (primesInSeq < k && rightPrime < n) {
rightPrime += jmp[rightPrime];
rightCount = jmp[rightPrime];
primesInSeq++;
}
if (primesInSeq < k || rightPrime == n) {
// less than k primes in sequence
outputSol(0);
return 0;
}
long long solutions = 0;
while (rightPrime < n) {
solutions += leftCount * rightCount;
leftCount = jmp[leftPrime];
leftPrime += jmp[leftPrime];
rightPrime += jmp[rightPrime];
rightCount = jmp[rightPrime];
}
outputSol(solutions);
return 0;
}