半数集问题(算法设计与分析)

2024-01-11 17:20

本文主要是介绍半数集问题(算法设计与分析),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

给定一个自然数n给定一个自然数n,由n 开始可以依次产生半数集set(n)中的数如下。
(1) n∈set(n);
(2) 在n 的左边加上一个自然数,但该自然数不能超过最近添加的数的一半;
(3) 按此规则进行处理,直到不能再添加自然数为止。
例如,set(6)={6,16,26,126,36,136}。半数集set(6)中有6 个元素。
注意半数集是多重集。
对于给定的自然数n,计算半数集set(n)中的元素个数。
输入样例:

6

输出样例:

6

算法设计
首先,先了解一下半数集是如何产生的,以set(6)为例,有如下图示:
在这里插入图片描述

我们找到了三个满足条件的数,即1、2、3,他们分别与6构成了16、26、36,依照这三个数继续向集合中添加元素,对于16,1是最近添加的数,但因为比1的一半小的自然数只有0,所以这一步就结束了。对于26,2是最近添加的数,1满足(2)的条件,所以将126也添加到了半数集中。同理,将136也添加到了半数集中。
由此,我们可以应用递归的思想,来解决问题,对于set(n)中的元素个数f(n),有以下公式:
在这里插入图片描述

设计的递归算法如下:

int halfset(int n){int sum = 1;for(int i=1;i<=n/2;i++){sum += halfset(i);}return sum;
}

该算法在n较大时,运行时间较长,原因是进行了很多重复的递归。比如n=16时,满足条件的数中有4和8,在对8进行递归中,也包含了4这个数,这样就产生了重复。我们可以设置一个数组,存放已经计算好的结果,改进算法的效率,改进的代码如下所示:

int a[1005]={0};
int dfs(int n){int sum = 1;if(a[n]>0)return a[n];for(int i=1;i<=n/2;i++){sum += dfs(i);}a[n]=sum;return sum;
}

完整代码:

#include<bits/stdc++.h>
using namespace std;
int a[1005]={0}; //存放已计算的数据
int halfset(int n){int sum = 1;if(a[n]>0) //如果f(n)已经得出,就不必再重复计算return a[n];for(int i=1;i<=n/2;i++){sum += halfset(i);}a[n]=sum;return sum;
}
int main()
{int n;FILE* fin=fopen("input.txt","r+");FILE* fout=fopen("output.txt","r+");fscanf(fin,"%d",&n);int result=halfset(n);cout << result <<endl;fprintf(fout,"%d",result);fclose(fin);fclose(fout);return 0;
}

规模 改进前 改进后
n=1000 7.648s 1.681s
n=1200 18.226s 1.738s

这篇关于半数集问题(算法设计与分析)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/595110

相关文章

解决IDEA使用springBoot创建项目,lombok标注实体类后编译无报错,但是运行时报错问题

《解决IDEA使用springBoot创建项目,lombok标注实体类后编译无报错,但是运行时报错问题》文章详细描述了在使用lombok的@Data注解标注实体类时遇到编译无误但运行时报错的问题,分析... 目录问题分析问题解决方案步骤一步骤二步骤三总结问题使用lombok注解@Data标注实体类,编译时

大数据小内存排序问题如何巧妙解决

《大数据小内存排序问题如何巧妙解决》文章介绍了大数据小内存排序的三种方法:数据库排序、分治法和位图法,数据库排序简单但速度慢,对设备要求高;分治法高效但实现复杂;位图法可读性差,但存储空间受限... 目录三种方法:方法概要数据库排序(http://www.chinasem.cn对数据库设备要求较高)分治法(常

Vue项目中Element UI组件未注册的问题原因及解决方法

《Vue项目中ElementUI组件未注册的问题原因及解决方法》在Vue项目中使用ElementUI组件库时,开发者可能会遇到一些常见问题,例如组件未正确注册导致的警告或错误,本文将详细探讨这些问题... 目录引言一、问题背景1.1 错误信息分析1.2 问题原因二、解决方法2.1 全局引入 Element

关于@MapperScan和@ComponentScan的使用问题

《关于@MapperScan和@ComponentScan的使用问题》文章介绍了在使用`@MapperScan`和`@ComponentScan`时可能会遇到的包扫描冲突问题,并提供了解决方法,同时,... 目录@MapperScan和@ComponentScan的使用问题报错如下原因解决办法课外拓展总结@

MybatisGenerator文件生成不出对应文件的问题

《MybatisGenerator文件生成不出对应文件的问题》本文介绍了使用MybatisGenerator生成文件时遇到的问题及解决方法,主要步骤包括检查目标表是否存在、是否能连接到数据库、配置生成... 目录MyBATisGenerator 文件生成不出对应文件先在项目结构里引入“targetProje

C#使用HttpClient进行Post请求出现超时问题的解决及优化

《C#使用HttpClient进行Post请求出现超时问题的解决及优化》最近我的控制台程序发现有时候总是出现请求超时等问题,通常好几分钟最多只有3-4个请求,在使用apipost发现并发10个5分钟也... 目录优化结论单例HttpClient连接池耗尽和并发并发异步最终优化后优化结论我直接上优化结论吧,

Java内存泄漏问题的排查、优化与最佳实践

《Java内存泄漏问题的排查、优化与最佳实践》在Java开发中,内存泄漏是一个常见且令人头疼的问题,内存泄漏指的是程序在运行过程中,已经不再使用的对象没有被及时释放,从而导致内存占用不断增加,最终... 目录引言1. 什么是内存泄漏?常见的内存泄漏情况2. 如何排查 Java 中的内存泄漏?2.1 使用 J

numpy求解线性代数相关问题

《numpy求解线性代数相关问题》本文主要介绍了numpy求解线性代数相关问题,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧... 在numpy中有numpy.array类型和numpy.mat类型,前者是数组类型,后者是矩阵类型。数组

解决systemctl reload nginx重启Nginx服务报错:Job for nginx.service invalid问题

《解决systemctlreloadnginx重启Nginx服务报错:Jobfornginx.serviceinvalid问题》文章描述了通过`systemctlstatusnginx.se... 目录systemctl reload nginx重启Nginx服务报错:Job for nginx.javas

Redis主从/哨兵机制原理分析

《Redis主从/哨兵机制原理分析》本文介绍了Redis的主从复制和哨兵机制,主从复制实现了数据的热备份和负载均衡,而哨兵机制可以监控Redis集群,实现自动故障转移,哨兵机制通过监控、下线、选举和故... 目录一、主从复制1.1 什么是主从复制1.2 主从复制的作用1.3 主从复制原理1.3.1 全量复制