poj1047

题目不难。高精度乘法运算+判断循环数

给定一个长度为n的整数,注意有前导0,并算数字的一部分,若该数字满足:对所有n*pivot=cyclic(n),其中pivot为1、2、……、n数字的长度。cyclic(n)表示n的循环数。则n为循环数,否则不是循环数。

分析如下:首先将数字转化为数组,可有前导0,不影响乘法结果。然后依次枚举每个pivot,进行高精度乘法运算。对运算结果判断是否为n的循环数,若全部都是则说明是循环数,否则不是循环数。

这里,进行高精度乘法运算时要注意一点:

当真实结果(去除前导0)的长度大于n的长度时,则说明一定不是n的循环数;若小于或等于n的长度,则应该补充前导0直至长度相同。

判断循环数其实就是一个取模问题,这里不说明,详见注释:

下面是代码:168K+0MS

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define Max 1000
char Input[Max]; //输入整数字符串
int trans[Max]; // 将整数字符串转化为整数数组
int midd[Max]; //存储1——n长度之间数 : 转化为整数数组
int result[Max]; //存储乘法结果
int len_trans,len_midd,len_result; //长度
bool Is_circle(){ // 判断是否为循环数,取模是关键
	for(int i=0;i<len_trans;i++){ //枚举起点
		int j=i,num=0,pivot=0;
		while(true){
			if(trans[j]!=result[pivot])
				break;
			else{
				num++;
				pivot++;
				if(num==len_trans)
					return true;
				j=(j+1)%len_trans; //重点
			}
		}
	}
	return false;
}
bool epo(){ //高精度乘法运算
	int i,j;
	memset(result,0,sizeof(result));
	for(i=0;i<len_trans;i++)
		for(j=0;j<len_midd;j++)
			result[i+j]+=trans[i]*midd[j];
	for(i=0;i<Max;i++)
		if(result[i]>=10){			
			result[i+1]+=result[i]/10;
			result[i]%=10;
		}
    for(i=Max-1;i>=0;i--)
		if(result[i]>0)
			break;
	if(i+1>len_trans) // 若实际长度大于n的长度,则一定不是n的循环数
		return false;
	return Is_circle(); // 否则可以适当补充0,判断是否为循环数
}
bool Is_cyclic(){ //判断n是否为循环数
	for(int i=1;i<=len_trans;i++){ //枚举1——n长度数字
		int temp=i,pivot=0;
		while(temp>0){ //转化为数组
			midd[pivot++]=temp%10;
			temp/=10;
		}
		len_midd=pivot;
		if(!epo()) //若存在一个不是n的循环数,则说明n不是循环数
			return false;
	}
	return true;
}
int main(){
	while(scanf("%s",Input)!=EOF){
		getchar();
		int len=strlen(Input);
		for(int i=len-1;i>=0;i--) //转化为整数数组
			trans[len-i-1]=Input[i]-'0';
		len_trans=len;
		if(Is_cyclic()) //判断是否为循环数
			printf("%s is cyclic\n",Input);
		else
			printf("%s is not cyclic\n",Input);
	}
	return 0;
}


 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值