【C语言基础】->哥德巴赫猜想验证->筛选法->算法极限优化之你不可能比我快

Ⅰ 哥德巴赫猜想

哥德巴赫1742年给欧拉的信中哥德巴赫提出了以下猜想:任一大于2的偶数都可写成两个质数之和。但是哥德巴赫自己无法证明它,于是就写信请教赫赫有名的大数学家欧拉帮忙证明,但是一直到死,欧拉也无法证明。因现今数学界已经不使用“1也是素数”这个约定,原初猜想的现代陈述为:任一大于5的整数都可写成三个质数之和。欧拉在回信中也提出另一等价版本,即任一大于2的偶数都可写成两个质数之和。今日常见的猜想陈述为欧拉的版本。把命题"任一充分大的偶数都可以表示成为一个素因子个数不超过a个的数与另一个素因子不超过b个的数之和"记作"a+b"。1966年陈景润证明了"1+2"成立,即"任一充分大的偶数都可以表示成二个素数的和,或是一个素数和一个半素数的和"。
今日常见的猜想陈述为欧拉的版本,即任一大于2的偶数都可写成两个素数之和,亦称为“强哥德巴赫猜想”或“关于偶数的哥德巴赫猜想”。

简单来说就是,任何一个大于2的偶数都可以分解成两个素数。

这篇博客会分四个层次,将一个普通代码优化到极限。

Ⅱ 最低级算法

哥德巴赫猜想的验证由三个部分组成:判断质数,判断偶数是否可以分解成两个质数,最后判断一个范围内哥德巴赫猜想是否正确。
以下为最简单最基础的代码,同时也是优化空间最大的👇

#include <stdio.h>
#include <time.h>

#define TRUE   1
#define FALSE  0

typedef unsigned char boolean;

boolean isPrime(int num);
boolean resolve(int num);
void inspect(int ceiling);

void inspect(int ceiling) {
   
	int i;

	for (i = 4; i <= ceiling; i += 2) {
   
		if (!resolve(i)) {
   
			printf("哥德巴赫猜想被证伪了!\n");
			return;
		}
	}
	printf("哥德巴赫果然很厉害!\n");	
}

boolean resolve(int num) {
   
	int i;

	if (isPrime(num - 2)) {
   
		return TRUE;
	}
	for (i = 3; i <= num / 2; i += 2) {
   
		if (isPrime(i) && isPrime(num - i)) {
   
			return TRUE;
		}
	}
	return FALSE;
}

boolean isPrime(int num) {
   
	int i;

	for (i = 2; i < num && num % i; i++) {
   
		;
	}
	return i >= num;
}

int main() {
   
	int ceiling;
	long startTime;
	long endTime;

	printf("请输入验证哥德巴赫猜想的最大数:");
	scanf("%d", &ceiling);

	startTime = clock();
	inspect(ceiling);
	endTime = clock();

	endTime -= startTime;

	printf("消耗时间:%d.%03ds", endTime / 1000, endTime % 1000);
	printf("\n");

	return 0;
}

测试结果如下,我们要验证100 000以下的偶数是否成立👇
在这里插入图片描述

可以看到,100 000以下的数耗时5.991秒,我们再验证1 000 000的👇
在这里插入图片描述
可以看到,我的小破电脑居然用了这么久才验证成功,即使只是增了一个0。正经人谁会等一个程序运行这么长时间啊,所以我们要逐步将其优化,将程序优化至一个正常人可以忍受的程度。

Ⅲ 没那么低级算法-> 质数判断算法优化

在最低级的代码中,我们判断质数用的是以下的代码👇

boolean isPrime(int num) {
   
	int i;

	for (i = 2; i < num && num % i; i++) {
   
		;
	}
	return i >= num;
}

尽管已经足够简单,但其仍要进行一个很大的循环,每次分解一个数时都要做两次这样的循环,很浪费时间,所以第一层优化,我们先减少查询质数的循环所消耗的时间。
我之前的循环,要让i = 2一直判断到num - 1,从这里面来判断num是否有因子将其整除,我以120为例子,提供一个新的视角。

120 / 2 = 60&

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值