有趣的算法

目录:

1、百钱买百鸡

2、韩信点兵

1)概述 2)正常取余算法 3)循环算法


1、百钱买百鸡

我国古代《算经》中的"百钱买百鸡"问题:

鸡翁一,值钱五;鸡母一,值钱三;鸡雏三,值钱一;百钱买百鸡,则翁、母、雏各几何?

分析:

用数学方法解决。设鸡翁(公鸡)x只,鸡母(母鸡)y只,鸡雏(鸡仔)z只,可得到方程组如下:

作为限制条件,应该有:

|-------------|-------------------|-----------|
| 0 ≤ x ≤ 20 | 鸡翁不可能超过20只,均为正整数 | 20只 是100钱 |
| 0 ≤ y ≤ 33 | 鸡母不可能超过33只,均为正整数 | 33只是99钱 |
| 0 ≤ z ≤ 100 | 鸡雏不可能超过100只,均为正整数 | 必须为3的整倍数 |

运算量不大,可以利用三重循环得到结果。

cpp 复制代码
#include <stdio.h>
#include <math.h>
 
int accord( int i, int j, int k )
{
    if( 5*i + 3*j + k/3 == 100 && k%3 ==0 && i+j+k == 100 )
        return 1;      //如果是百钱百鸡,返回1,正确的结果
    else
        return 0;    //如果不是,返回0
}
 
int main(void)
{
    int i, j, k;      //i:鸡翁数;  j:鸡母数;  k:鸡雏数
    printf("100yuan for 100 chick:\n");
    
    for( i = 0; i <= 20; i++ )
        for( j = 0; j <= 33; j++ )
            for( k = 0; k <= 100; k++ )
                if( accord( i, j, k ) )
                {
                	printf("cock:%d\n",i);
                	printf("hen:%d\n",j);
                	printf("chicken:%d\n",k);
                }
    return 1;
}

C-Free验证代码:

C-Free代码下载地址:有趣的算法合集-1百钱买百鸡

2、韩信点兵

1)概述

韩信带1500名兵士打仗,战死四五百人,站3人一排,多出2人;站5人一排,多出4人;站7人一排,多出6人。韩信马上说出人数:1049。

首先我们来了解一下同余的概念。a和b关于c同余,意思是说a除以c和b除以c的余数相同。例如:8÷5 = 1余3,3÷5 = 0余3,所以8和3关于5同余,写作8 ≡ 3(mod 5),其中mod读作"模"。而且,由于3小于5,所以3本身就是3除以5的余数,因此8 ≡ 3(mod 5)也可以理解为8除以5的余数是3。

这样,韩信点兵问题就可以表示为数学语言了。有一个数字x,除以3余2,除以5余3,除以7余2, 那么这个数字是多少?数学写法是

对于这个问题,最基本的解法是穷举法,就是把满足每个条件的数字写出来,然后找到相同的数字。

除以3余数是2的数字有:2、5、8、11、14、17、20、23、26...

除以5余数是3 的数字有:3、8、13、18、23、28...

除以7余数是2的数字有:2、9、16、23、30...我们发现,满足三个条件的第一个数字是23。所以23是这个问题的一个解。

但是,这个问题的解并不是唯一的。3、5、7彼此互质,它们的最小公倍数是105。也就是说,105除以3、除以5或者除以7都没有余数。如果一个数字x是满足要求的,那么在x上加上几个105都不会改变它对3、5、7的余数。比如,23是满足要求的,那么23+105 = 128也是满足要求的,23+210 = 233也是满足要求的。

所以这个问题最后的解就是23+105n,其中n = 0,1,2,3...

2)正常取余算法

cpp 复制代码
//正常取余算法
#include <stdio.h>
#include <math.h>

int main(void)
{
	int x, y, z;
	int i;
    
	scanf("%d%d%d", &x, &y, &z);
	for (i = 0; i <= 1500; i++)
	{
		if (i%3 == x && i%5 == y && i%7 == z)
		{
			printf("%d\n", i);
		}
	}
	if (i > 10000)
		printf("No answer");
}

C-Free验证代码:

3)循环算法

cpp 复制代码
//循环算法
#include <stdio.h>
int main(void)
{
	int a,b,c;
	int x,y,z,j;
	int i;
	int f=0;
    
	scanf("%d%d%d",&a,&b,&c);
	for(i=3;i<=34;i++)
	{
		int sum=3*i+a;
		for(j=2;j<=20;j++)
		{
			if(((j*5)+b)==sum&&f==0)
			{
				for(z=1;z<15;z++)
				{
					if(((z*7)+c)==sum&&f==0)
					{
						printf("%d",sum);
						f=1;
						break;
					}
				}	
			}
			if(f==1)
			break;
		}
		if(f==1)
		break;
	}
    
	if(f==0)
	printf("No answer");
	return 0;
}

C-Free验证代码:

C-Free代码下载地址:有趣的算法合集-2韩信点兵


路虽远,行则将至;事虽难,做则可成。觉得不错,动动发财的小手点个赞哦!

相关推荐
一点媛艺2 小时前
Kotlin函数由易到难
开发语言·python·kotlin
姑苏风2 小时前
《Kotlin实战》-附录
android·开发语言·kotlin
奋斗的小花生3 小时前
c++ 多态性
开发语言·c++
魔道不误砍柴功3 小时前
Java 中如何巧妙应用 Function 让方法复用性更强
java·开发语言·python
pianmian13 小时前
python数据结构基础(7)
数据结构·算法
闲晨3 小时前
C++ 继承:代码传承的魔法棒,开启奇幻编程之旅
java·c语言·开发语言·c++·经验分享
老猿讲编程3 小时前
一个例子来说明Ada语言的实时性支持
开发语言·ada
UestcXiye4 小时前
《TCP/IP网络编程》学习笔记 | Chapter 3:地址族与数据序列
c++·计算机网络·ip·tcp
Chrikk4 小时前
Go-性能调优实战案例
开发语言·后端·golang
幼儿园老大*4 小时前
Go的环境搭建以及GoLand安装教程
开发语言·经验分享·后端·golang·go