乘积最大

题目的链接为: http://acm.njupt.edu.cn/acmhome/problemdetail.do?&method=showdetail&id=1017
题目的描述为:
乘积最大
时间限制(普通/Java):1000MS/3000MS          运行内存限制:65536KByte
总提交:228            测试通过:100

描述


今年是国际数学联盟确定的“2000——世界数学年”,又恰逢我国著名数学家华罗庚先生诞辰90周年。在华罗庚先生的家乡江苏金坛,组织了一场别开生面的数学智力竞赛的活动,你的一个好朋友XZ也有幸得以参加。活动中,主持人给所有参加活动的选手出了这样一道题目:

    设有一个长度为N的数字串,要求选手使用K个乘号将它分成K+1个部分,找出一种分法,使得这K+1个部分的乘积能够为最大。

    同时,为了帮助选手能够正确理解题意,主持人还举了如下的一个例子:

有一个数字串:312, 当N=3,K=1时会有以下两种分法:

1)  3*12=36

2)  31*2=62

这时,符合题目要求的结果是:31*2=62

现在,请你帮助你的好朋友XZ设计一个程序,求得正确的答案。


输入


输入共有两行:

第一行共有2个自然数N,K(6≤N≤40,1≤K≤6)

第二行是一个长度为N的数字串。


输出


输出所求得的最大乘积(一个自然数),答案在long long 数据范围之内。


样例输入

4  2
1231

样例输出

62

我觉得这道题只能用JAVA解,因为JAVA提供了大整数BigInteger,要不然无法满足题目对n的长度40的要求。我看过AC的C程序代码,处理40 6时的结果是错的。
我的整个方法比较常规和傻,因为是求如何切分数字(指定切分个数),使得各个部分的总乘积最大。我第一个反应想到的就是搜索算法。
我们假设a[i][j]表示从下标为i乘到下标j的结果,那么要让它最大,肯定是:
a[i][j]=max{a[i][k]*a[k+1][j]}(i<=k<j)
知道这个后,从0开始搜索,得到最大的record即是结果。
用JAVA实现,时间为226MS,还是可以的。
Java代码 复制代码
  1. import java.math.BigInteger;   
  2. import java.util.*;   
  3. //处理第1017题   
  4. public class Main {   
  5.   
  6.     private final int MAXNUM=41;   
  7.     private int[] num=new int[MAXNUM];   
  8.     private int[] result=new int[MAXNUM];   
  9.     private int k=0;   
  10.     private int n=0;   
  11.     private int index=-1;   
  12.     private boolean[] vis=new boolean[MAXNUM];   
  13.     private BigInteger record=new BigInteger("0");   
  14.     private BigInteger[][] r=new BigInteger[MAXNUM][MAXNUM];   
  15.        
  16.     public void search(int currentK,int i)   
  17.     {   
  18.         if(i>=n)   
  19.         {   
  20.             return;   
  21.         }   
  22.         if(currentK>k)   
  23.         {   
  24.             return;   
  25.         }   
  26.         if(currentK==k)   
  27.         {   
  28.             BigInteger temp=new BigInteger("1");   
  29.             for(int j=0;j<=index;j++)   
  30.             {   
  31.                 if(j==0)   
  32.                 {   
  33.                     temp=temp.multiply(r[0][result[j]]);   
  34.                     if(j==index&&result[j]+1<=n-1)   
  35.                     {   
  36.                         temp=temp.multiply(r[result[j]+1][n-1]);   
  37.                     }   
  38.                 }   
  39.                 else  
  40.                 {   
  41.                     temp=temp.multiply(r[result[j-1]+1][result[j]]);   
  42.                     if(j==index&&result[j]+1<=n-1)   
  43.                     {   
  44.                         temp=temp.multiply(r[result[j]+1][n-1]);   
  45.                     }   
  46.                 }   
  47.             }   
  48.             if(temp.compareTo(record)>0)   
  49.             {   
  50.                 record=temp;   
  51.             }   
  52.         }   
  53.         else  
  54.         {   
  55.             for(int j=i;j<n-1;j++)   
  56.             {   
  57.                 if(vis[j]==false)   
  58.                 {   
  59.                     vis[j]=true;   
  60.                     result[++index]=j;   
  61.                     search(currentK+1,j);   
  62.                     index--;   
  63.                     vis[j]=false;   
  64.                 }   
  65.             }   
  66.         }   
  67.     }   
  68.     //输入   
  69.     public Main()   
  70.     {   
  71.         Scanner scan=new Scanner(System.in);   
  72.            
  73.         n=scan.nextInt();   
  74.         k=scan.nextInt();   
  75.         String str=scan.next();   
  76.         for(int i=0;i<n;i++)   
  77.         {   
  78.             num[i]=Integer.parseInt(str.substring(i,i+1));   
  79.         }   
  80.         for(int i=0;i<MAXNUM;i++)   
  81.         {   
  82.             vis[i]=false;   
  83.         }   
  84.         for(int i=0;i<n;i++)   
  85.         {   
  86.             for(int j=i;j<n;j++)   
  87.             {   
  88.                 r[i][j]=new BigInteger("0");   
  89.                 for(int q=i;q<=j;q++)   
  90.                 {   
  91.                     BigInteger temp=new BigInteger(String.valueOf(num[q]));   
  92.                     if(j>i)   
  93.                     {   
  94.                         int qq=1;   
  95.                         for(;qq<=j-q;qq++)   
  96.                         {   
  97.                             temp=temp.multiply(new BigInteger("10"));   
  98.                         }   
  99.                     }   
  100.                     r[i][j]=r[i][j].add(temp);   
  101.                 }//for q   
  102.             }//for j   
  103.         }//for i   
  104.         search(0,0);   
  105.         System.out.println(record);   
  106.     }   
  107.     public static void main(String[] args)   
  108.     {   
  109.         Main main=new Main();   
  110.     }   
  111. }  


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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值