这道题无论横着,竖着,一行/列来整体放都会超时,想不到什么好办法。只好写了个超长的switch case语句,想清楚瞅仔细,就省得调试麻烦了。
//00-17-11-18-03
//21-04-22-08-15
//12-19-05-20-10
//23-07-24-06-16
//02-13-09-14-01
上图是处理顺序,从00--24. 实际只用了15个case,因为有一些是可以计算出来的。之所以是这个顺序是为了把循环次数小的case放前头。运行速度还是很快的。
/*
ID: zhangyc1
LANG: C++
TASK: prime3
*/
//00-17-11-18-03
//21-04-22-08-15
//12-19-05-20-10
//23-07-24-06-16
//02-13-09-14-01
#include <fstream>
#include <iostream>
#include <string>
#include <sstream>
#include <cstring>
#include <cstdlib>
#include <vector>
#include <algorithm>
using namespace std;
stringstream os;
ofstream fileout("prime3.out");
int nFirstNum, nCommonSum;
// 因为sqrt(99999)=316.23,计算base为
int arrBasePrimeSet[100], nSizeBasePrimeSet = 0;
bool arrIsPrime[10][10][10][10][10];
bool bFound = false;
int arrMul[5] = {10000, 1000, 100, 10, 1};
int arrLastNum[4] = {1, 3, 7, 9};
int arrSumLine[5], arrSumCol[5], arrSumDia[2];
vector<string> vtRs;
int arrNum[5][5];
void getBasePrimeSet()
// 筛法求2-317内素数
{
bool arrIsPrime[318];
memset(arrIsPrime, 1, sizeof(arrIsPrime));
int nPos = 2;
while (nPos < 318)
{
arrBasePrimeSet[nSizeBasePrimeSet] = nPos;
nSizeBasePrimeSet++;
int nThresh = 317 / nPos;
for (int i = 2; i < nThresh; i++)
{
arrIsPrime[i * nPos] = false;
}
nPos++;
while (nPos < 318 && arrIsPrime[nPos] == false)
nPos++;
}
}
// 10000至99999内满足和为nCommonSum
void getValidPrimeSet()
{
int arrDigit[5];
for (int i = 10001; i <= 99999; i++)
{
int nTemp = i;
for (int j = 4; j >= 0; j--)
{
arrDigit[j] = nTemp % 10;
nTemp /= 10;
}
if (arrDigit[0] + arrDigit[1] + arrDigit[2] + arrDigit[3] + arrDigit[4] == nCommonSum)
{
bool bValid = true;
for (int j = 0; j < nSizeBasePrimeSet; j++)
{
if (i % arrBasePrimeSet[j] == 0)
{
bValid = false;
break;
}
}
if (bValid)
{
arrIsPrime[arrDigit[0]][arrDigit[1]][arrDigit[2]][arrDigit[3]][arrDigit[4]] = true;
}
}
}
}
void prepairData()
{
ifstream filein("prime3.in");
filein >> nCommonSum >> nFirstNum;
filein.close();
memset(arrIsPrime, 0, sizeof(arrIsPrime));
}
void recordRs()
{
for (int i = 0; i < 5; i++)
{
for (int j = 0; j < 5; j++)
{
os << arrNum[i][j];
}
}
string str;
os >> str;
os.clear();
vtRs.push_back(str);
}
void dfs(int nDepth)
{
switch (nDepth)
{
case 0:
arrNum[0][0] = nFirstNum;
arrSumLine[0] = nFirstNum;
arrSumCol[0] = nFirstNum;
arrSumDia[0] = nFirstNum;
dfs(1);
break;
case 1:
for (int i = 0; i < 4; i++)
{
arrNum[4][4] = arrLastNum[i];
arrSumLine[4] += arrLastNum[i];
arrSumCol[4] += arrLastNum[i];
arrSumDia[0] += arrLastNum[i];
if (arrSumLine[4] <= nCommonSum && arrSumCol[4] <= nCommonSum && arrSumDia[0] <= nCommonSum)
{
dfs(2);
}
arrSumLine[4] -= arrLastNum[i];
arrSumCol[4] -= arrLastNum[i];
arrSumDia[0] -= arrLastNum[i];
}
break;
case 2:
for (int i = 0; i < 4; i++)
{
arrNum[4][0] = arrLastNum[i];
arrSumLine[4] += arrLastNum[i];
arrSumCol[0] += arrLastNum[i];
arrSumDia[1] += arrLastNum[i];
if (arrSumLine[4] <= nCommonSum && arrSumCol[0] <= nCommonSum && arrSumDia[1] <= nCommonSum)
{
dfs(3);
}
arrSumLine[4] -= arrLastNum[i];
arrSumCol[0] -= arrLastNum[i];
arrSumDia[1] -= arrLastNum[i];
}
break;
case 3:
for (int i = 0; i < 4; i++)
{
arrNum[0][4] = arrLastNum[i];
arrSumLine[0] += arrLastNum[i];
arrSumCol[4] += arrLastNum[i];
arrSumDia[1] += arrLastNum[i];
if (arrSumLine[0] <= nCommonSum && arrSumCol[4] <= nCommonSum && arrSumDia[1] <= nCommonSum)
{
dfs(4);
}
arrSumLine[0] -= arrLastNum[i];
arrSumCol[4] -= arrLastNum[i];
arrSumDia[1] -= arrLastNum[i];
}
break;
case 4:
for (int i = 0; i <= 9; i++)
{
arrNum[1][1] = i;
arrSumLine[1] += i;
arrSumCol[1] += i;
arrSumDia[0] += i;
if (arrSumLine[1] <= nCommonSum && arrSumCol[1] <= nCommonSum && arrSumDia[0] <= nCommonSum)
{
dfs(5);
}
arrSumLine[1] -= i;
arrSumCol[1] -= i;
arrSumDia[0] -= i;
}
break;
case 5:
for (int i = 0; i <= 9; i++)
{
int nLeft = nCommonSum - i - arrSumDia[0];
if (nLeft >= 0 && nLeft <= 9 && arrIsPrime[arrNum[0][0]][arrNum[1][1]][i][nLeft][arrNum[4][4]])
{
arrNum[2][2] = i;
arrNum[3][3] = nLeft;
arrSumLine[2] += i, arrSumLine[3] += nLeft;
arrSumCol[2] += i, arrSumCol[3] += nLeft;
arrSumDia[0] = nCommonSum;
arrSumDia[1] += i;
dfs(7);
arrSumLine[2] -= i, arrSumLine[3] -= nLeft;
arrSumCol[2] -= i, arrSumCol[3] -= nLeft;
arrSumDia[0] = nCommonSum - i - nLeft;
arrSumDia[1] -= i;
}
}
break;
case 7:
for (int i = 0; i <= 9; i++)
{
int nLeft = nCommonSum - i - arrSumDia[1];
if (nLeft >= 0 && nLeft <= 9 && arrIsPrime[arrNum[4][0]][i][arrNum[2][2]][nLeft][arrNum[0][4]])
{
arrNum[3][1] = i;
arrNum[1][3] = nLeft;
arrSumLine[3] += i, arrSumLine[1] += nLeft;
arrSumCol[1] += i, arrSumCol[3] += nLeft;
arrSumDia[1] = nCommonSum;
dfs(9);
arrSumLine[3] -= i, arrSumLine[1] -= nLeft;
arrSumCol[1] -= i, arrSumCol[3] -= nLeft;
arrSumDia[1] = nCommonSum - i - nLeft;
}
}
break;
case 9:
for (int i = 0; i < 4; i++)
{
arrNum[4][2] = arrLastNum[i];
arrSumLine[4] += arrLastNum[i];
arrSumCol[2] += arrLastNum[i];
if (arrSumLine[4] <= nCommonSum && arrSumCol[2] <= nCommonSum)
{
dfs(10);
}
arrSumLine[4] -= arrLastNum[i];
arrSumCol[2] -= arrLastNum[i];
}
break;
case 10:
for (int i = 0; i < 4; i++)
{
arrNum[2][4] = arrLastNum[i];
arrSumLine[2] += arrLastNum[i];
arrSumCol[4] += arrLastNum[i];
if (arrSumLine[2] <= nCommonSum && arrSumCol[4] <= nCommonSum)
{
dfs(11);
}
arrSumLine[2] -= arrLastNum[i];
arrSumCol[4] -= arrLastNum[i];
}
break;
case 11:
for (int i = 1; i <= 9; i++)
{
arrNum[0][2] = i;
arrSumLine[0] += i;
arrSumCol[2] += i;
if (arrSumLine[0] <= nCommonSum && arrSumCol[2] <= nCommonSum)
{
dfs(12);
}
arrSumLine[0] -= i;
arrSumCol[2] -= i;
}
break;
case 12:
for (int i = 1; i <= 9; i++)
{
arrNum[2][0] = i;
arrSumLine[2] += i;
arrSumCol[0] += i;
if (arrSumLine[2] <= nCommonSum && arrSumCol[0] <= nCommonSum)
{
dfs(13);
}
arrSumLine[2] -= i;
arrSumCol[0] -= i;
}
break;
case 13:
for (int i = 0; i < 4; i++)
{
int nLeft = nCommonSum - arrSumLine[4] - arrLastNum[i];
if (nLeft > 0 && nLeft <= 9 && arrIsPrime[arrNum[4][0]][arrLastNum[i]][arrNum[4][2]][nLeft][arrNum[4][4]])
{
arrNum[4][1] = arrLastNum[i], arrNum[4][3] = nLeft;
arrSumLine[4] = nCommonSum;
arrSumCol[1] += arrLastNum[i], arrSumCol[3] += nLeft;
dfs(15);
arrSumLine[4] -= nLeft + arrLastNum[i];
arrSumCol[1] -= arrLastNum[i], arrSumCol[3] -= nLeft;
}
}
break;
case 15:
for (int i = 0; i < 4; i++)
{
int nLeft = nCommonSum - arrSumCol[4] - arrLastNum[i];
if (nLeft > 0 && nLeft <= 9 && arrIsPrime[arrNum[0][4]][arrLastNum[i]][arrNum[2][4]][nLeft][arrNum[4][4]])
{
arrNum[1][4] = arrLastNum[i], arrNum[3][4] = nLeft;
arrSumCol[4] = nCommonSum;
arrSumLine[1] += arrLastNum[i], arrSumLine[3] += nLeft;
dfs(17);
arrSumCol[4] -= nLeft + arrLastNum[i];
arrSumLine[1] -= arrLastNum[i], arrSumLine[3] -= nLeft;
}
}
break;
case 17:
for (int i = 1; i <= 9; i++)
{
int nLeft1 = nCommonSum - arrSumLine[0] - i;
int nLeft2 = nCommonSum - arrSumCol[1] - i;
int nLeft3 = nCommonSum - arrSumLine[2] - nLeft2;
if (nLeft1 > 0 && nLeft1 <= 9 && nLeft2 >= 0 && nLeft2 <= 9 && nLeft3 >= 0 && nLeft3 <= 9 &&
nLeft1 + nLeft3 + arrSumCol[3] == nCommonSum &&
arrIsPrime[arrNum[0][0]][i][arrNum[0][2]][nLeft1][arrNum[0][4]] &&
arrIsPrime[arrNum[2][0]][nLeft2][arrNum[2][2]][nLeft3][arrNum[2][4]] &&
arrIsPrime[i][arrNum[1][1]][nLeft2][arrNum[3][1]][arrNum[4][1]] &&
arrIsPrime[nLeft1][arrNum[1][3]][nLeft3][arrNum[3][3]][arrNum[4][3]])
{
arrNum[0][1] = i, arrNum[0][3] = nLeft1, arrNum[2][1] = nLeft2, arrNum[2][3] = nLeft3;
arrSumLine[0] = arrSumLine[2] = arrSumCol[1] = arrSumCol[3] = nCommonSum;
dfs(21);
arrSumLine[0] -= i + nLeft1, arrSumLine[2] -= nLeft2 + nLeft3;
arrSumCol[1] -= i + nLeft2, arrSumCol[3] -= nLeft1 + nLeft3;
}
}
break;
case 21:
for (int i = 1; i <= 9; i++)
{
int nLeft1 = nCommonSum - arrSumLine[1] - i;
int nLeft2 = nCommonSum - arrSumCol[0] - i;
int nLeft3 = nCommonSum - arrSumLine[3] - nLeft2;
if (nLeft2 > 0 && nLeft2 <= 9 && nLeft1 >= 0 && nLeft1 <= 9 && nLeft3 >= 0 && nLeft3 <= 9 &&
nLeft1 + nLeft3 + arrSumCol[2] == nCommonSum &&
arrIsPrime[i][arrNum[1][1]][nLeft1][arrNum[1][3]][arrNum[1][4]] &&
arrIsPrime[nLeft2][arrNum[3][1]][nLeft3][arrNum[3][3]][arrNum[3][4]] &&
arrIsPrime[arrNum[0][0]][i][arrNum[2][0]][nLeft2][arrNum[4][0]] &&
arrIsPrime[arrNum[0][2]][nLeft1][arrNum[2][2]][nLeft3][arrNum[4][2]])
{
arrNum[1][0] = i, arrNum[3][0] = nLeft2, arrNum[1][2] = nLeft1, arrNum[3][2] = nLeft3;
recordRs();
}
}
break;
}
}
void process()
{
getBasePrimeSet();
getValidPrimeSet();
dfs(0);
if (vtRs.size() == 0)
{
fileout << "NONE\n";
}
else
{
sort(vtRs.begin(), vtRs.end());
string strTemp;
for (vector<string>::const_iterator it = vtRs.begin(); it != vtRs.end(); it++)
{
if (it != vtRs.begin())
{
fileout << endl;
}
strTemp = *it;
fileout << strTemp.substr(0, 5) << "\n" << strTemp.substr(5, 5) << "\n" << strTemp.substr(10, 5) << "\n" << strTemp.substr(15, 5) << "\n"
<< strTemp.substr(20, 5) << "\n";
}
}
}
int main(){
prepairData();
process();
fileout.close();
return 0;
}