从蛮力到策略

本文通过百鸡问题和完美立方等式实例,介绍了穷举法的基本应用及其优化。通过限制变量范围和减少循环次数,降低了算法复杂度。同时,讨论了不同时间复杂度级别如O(1),O(logN)和O(n)的直观理解,并提供了记录代码执行时间的方法。
摘要由CSDN通过智能技术生成

实验主题:从蛮力到策略

  1. 实验目的
    1. 掌握穷举法(枚举法)的基本思想和实现方法。
    2. 能够通过分析问题对穷举法(枚举法)进行优化减少解空间的搜索范围。
    3. 理解算法复杂度的概念,熟悉并体会常见的时间复杂度。
  2. 实验任务及步骤

1百鸡问题

“鸡翁一,值钱五;鸡母一,值钱三;鸡雏三,值钱一。百钱买百鸡,问鸡翁、母、雏各几何?”

  • 在不甚思考的情况下(每种鸡都可能有0-100只)凭直觉写出蛮力法求解百鸡问题的基本思路并编程实现,思考该算法复杂度的渐进表达式。

设鸡翁为x,鸡母为y,鸡雏为z,x,y,z从0依次循环到100,满足5x+3y+1/3z=100,x+y+z=100的条件则有解。

  • 缩小三种鸡数量可能的范围,优化算法,减少计算量,此时算法复杂度是否减少?

是有减少

  • 进一步优化算法,能否降低算法的复杂度?请写出思路并编程实现。

减少循环,降低复杂度,减少未知数,y=(100-7*x)/4;

            z=100-x-y;

代码粘贴区:

1.

#include<iostream>

using namespace std;

int main()

{

   int x,y,z;

   for(x=0;x<=100;x++)

      for(y=0;y<=100;y++)

          for(z=0;z<=100;z++)

             {

                if(x+y+z==100&&5*x+3*y+z/3==100&&z%3==0)

                {

                   cout<<"公鸡数="<<x

                   <<"  母鸡数="<<y

                   <<"  小鸡数="<<z

                   <<endl;

                };

             };

   return 0;

}

2.

#include<iostream>

using namespace std;

int main()

{

   int x,y,z;

   for(x=0;x<=20;x++)

      for(y=0;y<=33;y++) 

          for(z=0;z<=100;z++)

          {

          if(x+y+z==100&&5*x+3*y+z/3==100&&z%3==0)

             {

                cout<<"公鸡数="<<x

                <<"  母鸡数="<<y

                <<"  小鸡数="<<z

                <<endl;

             };

          }

   return 0;

}

3.

#include<iostream>

using namespace std;

int main()

{

   int x,y,z;

   for(x=0;x<=20;x++) 

          { 

             y=(100-7*x)/4;

             z=100-x-y;

             if(z>=0&&y>=0&&5*x+3*y+z/3==100&&z%3==0)

             {

                cout<<"公鸡数="<<x

                <<"  母鸡数="<<y

                <<"  小鸡数="<<z

                <<endl;

             };

          }

   return 0;

}

运行结果截图:

1.

2.

3.

 

  • 调整输入规模(如1000鸡1000钱问题、2000鸡2000钱问题等),观察并记录至少5组(每组多次运行取平均值)不同输入规模下任务1和任务3算法的运行时间,制作excel图表进行对比。

2)掌握枚举算法的基本思想和实现方法。

任务描述: 如a3= b3 + c3 + d3的等式被称为完美立方等式。例如 123= 63 + 83 + 103 。编写一个程序,对任给的正整数N (N≤100),寻找所有的四元组(a, b, c, d),使得等式成立,其中a,b,c,d 大于 1, 小于等于N,且 b<=c<=d。

输入:一个正整数N (N≤100)。 

输出:每行输出一个完美立方。输出格式为:a^3=b^3+c^3+d^3。 其中a,b,c,d所在位置分别用实际求出四元组值代入。

请按照a的值,从小到大依次输出。当两个完美立方等式中a值相同时,b值小的优先输出,若b仍相同,c值小的优先输出,c再相同时d值小的先输出。

样例输入

24

样例输出

6^3=3^3+4^3+5^3

12^3=6^3+8^3+10^3

18^3=2^3+12^3+16^3

18^3=9^3+12^3+15^3

19^3=3^3+10^3+18^3

20^3=7^3+14^3+17^3

24^3=12^3+16^3+20^3

代码粘贴区:

#include<iostream>

using namespace std;

int main(){

   int a,b,c,d;

   int N;

   cout<<"输入N";

   cin>>N;

   for(a=2;a<=N;a++){

      for(b=2;b<=a;b++)

         for(c=b;c<=a;c++)

            for(d=c;d<=a;d++){

               if(a*a*a==b*b*b+c*c*c+d*d*d)

               cout<<a<<"^3="<<b<<"^3+"<<c<<"^3+"<<d<<"^3"<<endl;

         }

        

     

   }

   return 0;

}

运行结果截图:

3)理解完美立方问题和求年龄问题的求解思路。

任务描述:年龄几何:张三、李四、王五、刘六的年龄成一等差数列,他们四人的年龄相加是26,相乘是 880,求以他们的年龄为前4项的等差数列的前20项。

思路:先穷举出4个人的年龄在找出等差关系,用for循环求出前20

实验总结

(1)为什么不使用时间单位来表示时间复杂度。

(2)谈谈你对不同量级时间复杂度的直观认识。

(1)用时间单表示的话,这种方式非常容易受运行环境的影响,在性能高的机器上跑出来的结果与在性能低的机器上跑的结果相差会很大。而且对测试时使用的数据规模也有很大关系。时间复杂度是用来表示代码执行时间的增长变化趋势的。

(2)O(1):算法复杂度和问题规模无关。

O(logN):数据量大幅增加时,消耗时间/空间只有少量增加.

O(n):随着样本数量的增加,复杂度也随之线性增加

编程提示

如何记录一段代码的执行时间:

C语言: #include <time.h> int start=clock();int end=clock();int t=end-start;

JAVA:long startTime=System.currentTimeMillis();

long endTime=System.currentTimeMillis();

long Time=endTime-startTime;

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值