鱼C论坛

 找回密码
 立即注册
查看: 4149|回复: 8

[争议讨论] 算法每日一题(六)—___穷举法

[复制链接]
发表于 2011-7-8 23:17:06 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能^_^

您需要 登录 才可以下载或查看,没有账号?立即注册

x
本帖最后由 LNH_Sniper 于 2011-7-8 23:17 编辑

问题:TOM共有5本新书,要借给A、B、C3位同学,每人只能借一本书,则TOM可以有多少种不同的借书方**

提示:本题目是典型的穷举法的应用,属于简单题
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
发表于 2011-7-9 08:13:50 | 显示全部楼层
最多能借一本  最少可不可以不借
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
 楼主| 发表于 2011-7-9 09:38:06 | 显示全部楼层
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
发表于 2011-7-9 10:17:11 | 显示全部楼层
恩  这题挺锻炼思想的  实际上是吧实际问题转化为抽象的概念, 这个问题和彩票选数差不多  每个数字是1-5,5选3,所有都列举就可以了呗
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
发表于 2011-7-9 12:26:33 | 显示全部楼层
考虑这个问题的一般化,把m本书借给n个人,每人必须且只能借一本。
假设有f(m,n)种借法,则:
f(m,n)=m*f(m-1,n-1)  (其中,m>=n)---  第一个人有m种选择,剩下m-1本书借给n-1个人
且有
f(x,0)=1  (其中x>=0)--- 把x本书借给0个人只有1种借法(就是不借)
所以用递归解这个问题是可以的。程序如下:
  1. #include<stdio.h>
  2. int f(int m, int n){
  3.         if(n==0) return 1;
  4.         return m*f(m-1,n-1);
  5. }
  6. int main(){
  7.         printf("%d\n",f(5,3));
  8. }
复制代码
其实数学好的话,直接算5*4*3也可以得到答案,不过这就和编程没什么关系了。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
 楼主| 发表于 2011-7-9 20:12:43 | 显示全部楼层
首先,穷举法是最为简单,也是最为直接,同时又是最为耗时的一种解决实际问题的算法思想。

穷诀法的基本思想是:在可能的解空间中穷举出每一种肯能的解,并对每个可能的解进行判断,从中得到答案。

其中最关键步骤是:划定问题的解体空间,并在该解空间中一一枚举每个可能的解。
这里需要注意的是:一、解空间必须覆盖问题的全部解。
                           二、解空间集合及问题的集合一定是离散的,简单的说就是集合中的元素是可列的、有限的。
------------------------------------------------------------------------------------------------------------------

问题分析:假设TOM的5本书进行编号{ 1,2,3,4,5 },每个同学可借到的书的范围就限定在     { 1,2,3,4,5}中,因此TOM的借书方案不肯能超过5*5*5=125种,所以,这125种借书方案可以构成的解空间为{( x1, x2, x3 )| 1<= xi <= 5 , 且 x1 != x2 != x3 }

由上所述,可以得到该算法为:
for( i = 1; i <= 5; i++ )
     for( j = 1; j <= 5; j++ )
          for( k = 1; k <= 5; k++ )
               if( i != j && j != k && i != k )

所以程序完整代码如下:
  1. #include "stdio.h"

  2. int main()
  3. {
  4. int i,j,k;
  5. int enter = 0;
  6. printf("There are differnet methods for TOM to distribute his book to A,B,C\n");
  7. for( i = 1; i <= 5; i++ )
  8. for( j = 1; j <= 5; j++ )
  9. for( k = 1; k <= 5; k++ )
  10. if( i != j && j != k && i != k )
  11. {
  12. enter++;
  13. printf("(%d,%d,%d)",i,j,k);
  14. if( enter == 10 )
  15. {
  16. printf("\n");
  17. enter = 0;
  18. }
  19. }

  20. return 0;
  21. }
复制代码



想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
发表于 2011-7-23 08:37:22 | 显示全部楼层
每次的理解都不一样
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
发表于 2011-9-13 17:20:13 | 显示全部楼层
LNH_Sniper 发表于 2011-7-9 20:12
首先,穷举法是最为简单,也是最为直接,同时又是最为耗时的一种解决实际问题的算法思想。

穷诀法的基本 ...
  1. for( i = 1; i <= 5; i++ )
  2.      for( j = 1; j <= 5; j++ )
  3.         if(i!=j)
  4.           for( k = 1; k <= 5; k++ )
  5.                if( j != k && i != k )
复制代码

这样写的话能减少循环次数
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
发表于 2014-3-10 16:26:35 | 显示全部楼层
这是离散数学里面的鸽巢原理 5!/(5-3)!  用代码 很简单的:lol:
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2024-4-27 13:09

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表