练习基础题《二》

Q:

小明假期同爸爸一起去书店,他选中了n本书,每本书的单价分别为:P1、P2、P3……Pn。不巧的是,小明的爸爸只带了M元钱,为了让小明渡过一个愉快的假期,爸爸仍然同意买书,但有一个要求,要小明从n本书中选出若干本,使得单价相加所得的和同M元最接近。你能够帮助小明解决这个问题吗?要求:总钱数M、书本数n以及各本书的价格从键盘或文件输入;如果有多种组合,应全部列出。

A:

解法①:利用二进制解决组合问题

按位与‘&’的计算规则:

两个数都为1时,才为1,否则为0;For example:

3&5=1; 3用二进制表达为  0011 ,5用二进制表达为   0101

  0011

  0101

=

  0001  =2*0*1=1;

每本书有两种情况,买与不买,一共2*6-1=63种情况,除去都不买特殊的情景,从1~63均可用二进制表示,

在按位与运算解决组合问题;

Code:

#include<iostream>
using namespace std;
#define MAX 100
int main()
{
    float price[MAX],sum=0,total,max=-1;
    int i,j,n,a[MAX];
    cout<<"Please enter the money of total"<<endl;
    cin>>total;
    cout<<"Please enter number of book"<<endl;
    cin>>n;              //输入书的种类 
    cout<<"please enter the price of book"<<endl;
    for(i=0;i<n;++i)
    cin>>price[i];       //分别输入每本书的价格 
    int m=1,k=1,count=0,pn;
    for(j=1;j<n;++j)
    {
      m=2*m+1;
      k<<=1;         //k按位左移 
    }
    for(i=1;i<=m;++i)
    {
      pn=0;
      sum=0.0;
      for(j=1;j<=k;j<<=1)
      {
        if((i&j)==j)
        sum=sum+price[pn];
        if(sum>total)
        break;
        pn++;
      }
      if(sum<=total)
      {
       if(sum>max)
       {
        count=1;
        a[count-1]=i;
        max=sum;
       }
       else if(sum==max)
       {
            count++;
            a[count--]=i;
       }
      }
    }
    cout<<"there is"<<count<<" groups"<<endl;
    for(i=0;i<count;++i)
    {
      pn=0;
      for(j=1;j<=k;j<<=1)
      {
      if((a[i]&j)==j)
      cout<<price[pn]<<" ";
      pn++;
      }
    }
    system("pause");
    return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值