POJ2109 Power of Cryptography

题意

这题是一个贪心神(经病)题。
众所周知,如果有x^n=p,那么如果我们知道p和n,x就唯一确定。那么现在问题来了,已知p和n怎么求x。
这道题数字大的吓人。1<p<10101,1<n<200,1<x<109

题解

这题好好教育了我们一下贪心算法之Double的性质。Double最多能存储10302之大,所以同时x的限制,x不会很大,这就导致浮点数精度这题直接用pow开方就能解了。

提交代码

#include <stdio.h>

int n;
double d;

int main(){
  while(scanf("%d%lf",&n,&d)!=EOF){
    printf("%.lf\n", pow(d, 1/(double)n));
  }
}

错误解法(不知道错在哪里)

我的思路是这样的:12347的结尾1位数一定和47相同,两位数一定和347相同,三位数一定和2347相同,以此类推。由于c++没办法高精度保存那么大的数字,所以改用了java高精度,同时需要去除结尾的0,否则123020的后面跟着20个0就没办法找了。
然而依然一直wa,还没找到错误原因,望大佬指正。

错误代码

import java.io.*;
import java.math.*;
import java.util.*;
import java.text.*;


public class Main
{
static int n;
static BigDecimal d;
static BigDecimal ans;
static Boolean flag = false;
static int zeronum = 0;
static BigDecimal zeros = BigDecimal.valueOf(0);
	Boolean isEq( BigDecimal a , BigDecimal b , BigDecimal c ){
		BigDecimal ac = a.remainder(c);
		BigDecimal bc = b.remainder(c);
		//System.out.printf("ac = %f,bc = %f,isEqing %d\n",ac,bc,ac.compareTo(bc));
		return ( ac.compareTo(bc) == 0);
	}

	void dfs( BigDecimal  a , BigDecimal b ){
		for( int i = 0 ; i < 10 ; i++ ){
			BigDecimal tmp = a.add(b.multiply(BigDecimal.valueOf(i)));
			BigDecimal tmp1 = tmp.pow( n );
			//System.out.printf("a = %f,b = %f,i = %d,tmp1 = %f,dfsing\n",a,b,i,tmp1);
			if( tmp1.compareTo(d) == 0 ) {
				//System.out.printf("tmp1 = %f,d = %f ,dfs end!\n",tmp1,d);
				ans = tmp;
				flag = true;
				return;
			}
			if( tmp1.compareTo(d) == 1 ) {
				//System.out.printf("tmp1 = %f,d = %f ,dfs end!!\n",tmp1,d);
				return;
			}
			if(isEq( d , tmp1 , b.multiply(BigDecimal.valueOf(10)) )){
				//System.out.printf("tmp = %f,tmp1 = %f ,dfsing\n",tmp,tmp1);
				dfs( tmp , b.multiply(BigDecimal.valueOf(10)) );
				if( flag ) return;
			}
		}
	}

	public static void main(String[] args) 
	{
		Scanner cin = new Scanner (new BufferedInputStream(System.in));

		while(cin.hasNext()){
		flag = false;
        n = cin.nextInt(); d = cin.nextBigDecimal();

		zeronum = 0;
		zeros = BigDecimal.valueOf(10).pow(n);

        //d = d.pow(n);

        //System.out.printf("%.0f\n",d);
        while( d.remainder(zeros).compareTo(BigDecimal.valueOf(0)) == 0 ){
        	d = d.divide(zeros);
        	zeronum++;
        }

        Main j = new Main();
        j.dfs( BigDecimal.valueOf(0) , BigDecimal.valueOf(1));
        ans = ans.multiply(BigDecimal.valueOf(10).pow(zeronum));
        System.out.printf("%.0f\n",ans);
    }
    cin.close();
    }
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值