Problem 49 : Prime permutations
The arithmetic sequence, 1487, 4817, 8147, in which each of the terms increases by 3330, is unusual in two ways: (i) each of the three terms are prime, and, (ii) each of the 4-digit numbers are permutations of one another.
There are no arithmetic sequences made up of three 1-, 2-, or 3-digit primes, exhibiting this property, but there is one other 4-digit increasing sequence.
What 12-digit number do you form by concatenating the three terms in this sequence?
C++ source code
#include <iostream>
#include <vector>
#include <set>
#include <iterator>
#include <cmath> // sqrt()
#include <cassert> // assert()
#include <ctime> // clock()
using namespace std;
class PE0049
{
private:
bool checkPrime(int number);
set<int> getDigits(int number);
bool checkArithmeticSequence(int term1, int term2, int term3);
public:
vector<int> findArithmeticSequence(int range_start, int range_end);
};
bool PE0049::checkPrime(int number)
{
double squareRoot=sqrt((double)number);
if (number%2 == 0 && number!=2)
{
return false;
}
for(int i=3;i<=(int)squareRoot;i+=2) // 3, 5, 7, ...(int)squareRoot
{
if (number % i == 0)
{
return false;
}
}
return true;
}
set<int> PE0049::getDigits(int number)
{
set<int> digits;
while(number > 0)
{
digits.insert(number%10);
number /= 10;
}
return digits;
}
bool PE0049::checkArithmeticSequence(int term1, int term2, int term3)
{
if (true == checkPrime(term2) && true == checkPrime(term3))
{
set<int> term1Digits = getDigits(term1);
set<int> term2Digits = getDigits(term2);
if (term1Digits == term2Digits)
{
set<int> term3Digits = getDigits(term3);
if (term2Digits == term3Digits)
{
return true;
}
}
}
return false;
}
vector<int> PE0049::findArithmeticSequence(int range_start, int range_end)
{
// The first arithmetic sequence, 1487, 4817, 8147,
int arithmeticSequenceArray[] = {1487, 4817, 8147};
vector<int> arithmeticSequence_vec;
arithmeticSequence_vec.assign(arithmeticSequenceArray,
arithmeticSequenceArray+sizeof(arithmeticSequenceArray)/sizeof(int));
// vector<int> arithmeticSequence_vec = {1487, 4817, 8147}; // C++11
vector<int> arithmeticSequence;
bool foundFirstSequence = false;
int term1, term2, term3;
for(int n=range_start; n<range_end; n++)
{
if (false == checkPrime(n))
{
continue;
}
term1 = n;
term2 = term1 + 3330;
term3 = term2 + 3330;
if (true == checkArithmeticSequence(term1, term2, term3))
{
arithmeticSequence.push_back(term1);
arithmeticSequence.push_back(term2);
arithmeticSequence.push_back(term3);
if (false == foundFirstSequence &&
arithmeticSequence_vec == arithmeticSequence)
{
arithmeticSequence.clear();// first sequence,1487,4817,8147
foundFirstSequence = true;
}
else
{
break; // the second arithmetic sequence is found
}
}
}
return arithmeticSequence;
}
int main()
{
// There are no arithmetic sequences made up of three 1-, 2-, or 3-digit primes,
// so let's search from 1000 to 9999
vector<int> resultArray;
PE0049 pe0049;
resultArray = pe0049.findArithmeticSequence(1000, 9999);
cout << "The 12-digit number is ";
copy(resultArray.begin(), resultArray.end(), ostream_iterator<int>(cout));
cout << " by concatenating the three terms in this sequence." << endl;
return 0;
}
Python source code
def checkPrime(number):
"""
check whether number is a prime
"""
if number%2 == 0 and number!=2 or number < 2:
return False
for i in range(3, int(number**0.5)+1, 2): # 3, 5, 7, ...(int)squareRoot\
if number % i == 0:
return False
return True
def checkarithmeticSequence_list(term1, term2, term3):
"""
check whether term1, term2 and term3 can made up of an arithmetic sequence
"""
if True == checkPrime(term2) and True == checkPrime(term3):
if set(list(str(term1))) == set(list(str(term2))) and\
set(list(str(term1))) == set(list(str(term3))):
return True
return False
def findArithmeticSequence_list(range_start, range_end):
"""
find arithmetic sequence from range_start to range_end
"""
firstArithmeticSequence_list = ['1487', '4817', '8147']
arithmeticSequence_list, foundFirstSequence = [], False
for n in range(range_start, range_end):
if False == checkPrime(n):
continue
term1, term2, term3 = n, n+3330, n+6660
if True == checkarithmeticSequence_list(term1, term2, term3):
arithmeticSequence_list.append(str(term1))
arithmeticSequence_list.append(str(term2))
arithmeticSequence_list.append(str(term3))
if firstArithmeticSequence_list == arithmeticSequence_list and \
False == foundFirstSequence:
arithmeticSequence_list.clear() # clear first sequence
foundFirstSequence = True
else:
break # the second arithmetic sequence is found
return "".join(arithmeticSequence_list)
def main():
print("The 12-digit number is",findArithmeticSequence_list(1000,9999),\
"by concatenating the three terms in this sequence.")
if __name__ == '__main__':
main()