【FOJ】Problem 1068 An Interesting Set

Problem 1068 An Interesting Set.

题意

  • 正数集合S满足:
    ①所有位上数的总和等于他们的乘积
    ②如果s在S中,那么2s也在S中
  • 输入:
    n,表示n个测试数据
    跟着n行k
  • 输出:
    集合S中第K小的数

思路

两个数组,一个flag[1000000]用于标记数字是否属于S,另一个ans[500]按从小到大顺序存放S的元素,len表示ans数组的长度
对len初始值设1,数字1进ans
对当前k:
①k<=len,直接输出ans[k-1]
②k>len,从ans[len-1]+1开始遍历,设当前遍历数字x:

  • flag[x]是否为0?
    是:按规则①计算,和等于积吗?不等于,x不符合S的要求,continue
    flag[x]为1,或计算后符合S要求:x放入ans中,len++,同时将flag[2x]置1
  • len==k结束遍历,输出ans[k-1]

笔记

  • 从ans[len-1]+1开始遍历
  • 一开始想直接把1-9都存进去,可是这样子做会导致4*4=16不符合规则,所以还是老老实实从1开始一个个算,不差这一点

代码

#include<cstdio>
int flag[1000000]={0}, ans[500] = {1};
int len = 1;

int main(){
	int n, k;
	int ji, he, temp;
	scanf("%d", &n);
	while(n--){
		scanf("%d", &k);
		if(k<=len){
			printf("%d\n", ans[k-1]);
		}else{
			for(int x=ans[len-1]+1; k>len; x++){
				if(flag[x]==0){
					ji = 1;
					he = 0;
					temp = x;
					while(temp){
						ji = ji*(temp%10);
						he = he + (temp%10);
						temp = temp/10;
					}
					if(ji!=he)
						continue;
				}
				ans[len++] = x;
				flag[2*x] = 1;
			}
			printf("%d\n", ans[k-1]);
		}
	}
	return 0;
}
发布了28 篇原创文章 · 获赞 0 · 访问量 329

猜你喜欢

转载自blog.csdn.net/qq_44531167/article/details/105128961