码迷,mamicode.com
首页 > 其他好文 > 详细

codechef Prime Palindromes 题解

时间:2014-05-04 09:18:17      阅读:334      评论:0      收藏:0      [点我收藏+]

标签:blog   class   code   ext   int   string   

给定一个数,求一个新数要大于等于这个数,而这个新数既要是palindromes回文又要是prime素数。

题目很简单,有人都使用取巧的方法保存好结果直接查表。

或者暴力法求解。

这里不使用保存表的方法,也不要用暴力法。- 这些方法都不好。

使用的技巧有:

1 而是使用next palindrome的技巧,只需要O(n),n是数位,可以认为是常数了。

2 判断素数的方法,时间效率是O(sqrt(n)), n是数值大小,如果是重复判断很多数是否是素数是有办法优化的,但是如果是单个素数判断的话,我还想不到,也找不到优化的方法。

不过怎么都好,下面程序假设它是需要重复判断数是素数的,那么就可以保持一个数组的方法,然后只需要判断这个数是否能被这个数组中小于这个数n的sqrt(n)除尽,就可以快速判断出这个数是否是素数了。

当然本题好像直接判断是否是素数就可以了。

原题:http://www.codechef.com/problems/PRPALIN/

全部实现上面的优化,那么程序还是非常繁琐的,也是出于学习的目的吧。

#include <assert.h>
#include <string>
#include <stdio.h>
#include <math.h>
#include <iostream>
using namespace std;

namespace{
	static const int MAX_NUM = 1100;
}

bool allNines(string a)
{
	bool nines = true;
	for (int i = 0; i < (int)a.size() && nines; i++)
	{
		if (a[i] != ‘9‘) nines = false;
	}
	return nines;
}

string nextPalindrome(string a)
{
	if (allNines(a))
	{
		a[0] = ‘1‘;
		for (int i = 1; i < (int)a.size(); i++)
		{
			a[i] = ‘0‘;
		}
		a.push_back(‘1‘);
		return a;
	}

	int mid = (a.size() >> 1);
	int L = mid - 1, R = mid + 1;
	if (a.size() % 2 == 0) R--;//确定中心

	int i = L, j = R;//查找不同点下标
	for ( ; i >= 0 && j < (int)a.size() && a[i] == a[j]; i--, j++);

	bool leftsmall = false;
	if (i < 0 || a[i] <= a[j]) leftsmall = true;//i<0排除了等于的情况了

	for ( ; i >= 0; i--, j++)
	{
		a[j] = a[i];
	}
	if (leftsmall)
	{
		int carry = 1;
		if (a.size() % 2)
		{
			a[mid]++;
			if (a[mid] > ‘9‘) a[mid] = ‘0‘;
			else carry = 0;
		}
		i = L, j = R;
		while (carry)
		{
			a[i]++;
			if (a[i] > ‘9‘) a[i] = ‘0‘;
			else carry = 0;
			a[j] = a[i];
			i--, j++;
		}
	}
	return a;
}

bool isPalindrome(string s)
{
	bool palin = true;
	for (int i = 0, j = int(s.size()) - 1; i < j; i++, j--)
	{
		if (s[i] != s[j]) palin = false;
	}
	return palin;
}

int PrimePalindromes()
{
	bool primes[MAX_NUM+1] = {0};
	for (int i = 2; i <= MAX_NUM; i++)
	{
		if (!primes[i])
		{
			for (int j = (i<<1); j <= MAX_NUM; j += i)
			{
				primes[j] = true;
			}
		}
	}
	int primeNums[MAX_NUM] = {0};
	int id = 0;
	for (int i = 2; i <= MAX_NUM; i++)
	{
		if (!primes[i]) primeNums[id++] = i;
	}

	string s;
	cin>>s;
	int sn = stoi(s);
	assert(1 <= sn && sn <= 1000000);
	if (!isPalindrome(s)) s = nextPalindrome(s);

	while (true)
	{
		sn = stoi(s);
		int sq = (int)sqrt((double)sn);
		bool isprimeNum = true;
		int i = 0;
		for ( ; primeNums[i] <= sq && i < id; i++)
		{
			if (sn % primeNums[i] == 0)
			{
				isprimeNum = false;
				break;
			}
		}
		if (isprimeNum) break;
		s = nextPalindrome(s);
	}
	cout<<s;
	return 0;
}




codechef Prime Palindromes 题解,布布扣,bubuko.com

codechef Prime Palindromes 题解

标签:blog   class   code   ext   int   string   

原文地址:http://blog.csdn.net/kenden23/article/details/24932635

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!