什么是半数集?
给定一个自然数n给定一个自然数n,由n开始可以依次产生半数集set(n)中的数如下。
- n∈set(n);
- 在n的左边加上一个自然数,但该自然数不能超过最近添加的数的一半;
- 按此规则进行处理,直到不能再添加自然数为止。
例如,set(6)={6,16,26,126,36,136}。半数集set(6)中有6个元素。
思路: 运用队列存储待处理(添加数字)的元素, 需要判断数字位数以调整判断的数字, 输出半数集的数量以及具体的半数集元素
非递归的代码
#include <iostream>
#include <vector>
#include <queue>
#include <cmath>
using namespace std;int checkDigit(int number){if(number == 0) return 1;int count = 0;// 使用循环除以 10 的幂,直到数字变为 0while (number > 0) {number /= 10;count++;}return count;
}vector<int> HalfSet(int n) {vector<int> result;queue<int> queue;result.clear(); // 清空下缓存, 去除垃圾值result.push_back(n);queue.push(n);
// int level = 0;while (!queue.empty()) {int current = queue.front(); // 取出队列头元素int current_level = checkDigit(current); // 元素位数int index = current / pow(10, current_level-1); // 元素第一个数字queue.pop();for (int i = 1; i <= index / 2; i++) {int next = current + i * pow(10, current_level);result.push_back(next);queue.push(next);}}return result;
}int main() {int n;cin >> n;vector<int> halfSubset = HalfSet(n);cout << "n=" << n << "的半数集元素个数="<<halfSubset.size()<<endl;cout << "半数集元素是"<<endl;for (int num : halfSubset) { // 输出半数集元素cout << num << " ";}return 0;
}
递归版本 (其实这题十分适合使用递归的) 只需要修改处理的函数即可, 返回半数集数量
int HalfSet2(int n){ // 返回半数集数量int sum = 1; // 自身也算是半数集的一个if(n <= 1) return 1;for(int i = 1; i <= n/2; i++){sum += set(n/2);}return sum;
}
该递归写法 可以用一数组存储其中的值以减少重复值的出现达到优化的效果
欢迎如果有大佬们看出有问题, 在评论区或是私聊我批评指正。谢谢!