1 条题解

  • 0
    @ 2026-2-4 16:49:35
    #include<bits/stdc++.h>
    using namespace std;
    
    // [1] 全局数组,标记1~1e8范围内的数是否为素数,true表示是素数
    bool prime[100000100];
    // [2] 存储生成的素数序列,按从小到大顺序排列
    int arr1[100100];
    // [3] 存储每次查询的k值
    int arr[100100]; 
    
    // [8] 线性筛(欧拉筛)函数,生成1~a范围内的所有素数并存储到arr1中
    void MakePrime(int a){
    	// [9] 初始化prime数组,默认所有数为素数(true)
    	memset(prime,true,sizeof(prime));
    	// [10] 记录已找到的素数个数,作为arr1数组的索引
    	int sum=0;
    	// [11] 遍历2到a的所有数,筛选素数
    	for(int i=2;i<=a;++i){
    		// [12] 如果当前数是素数,加入素数数组arr1
    		if(prime[i]){
    			arr1[sum++]=i;
    		}
    		// [13] 用已找到的素数去筛除当前数的倍数,保证每个合数只被最小素因子筛一次
    		for(int j=0;j<sum&&arr1[j]*i<=a;j++){
    			// [14] 标记i*arr1[j]为非素数
    			prime[i*arr1[j]]=false;
    			// [15] 如果i能被当前素数arr1[j]整除,说明arr1[j]是i的最小素因子,后续倍数会被更小素数筛除,直接跳出循环
    			if(i%arr1[j]==0){
    				break;
    			}
    		}
    	}
    }
    
    int main(){
    	// [4] 定义变量:m为查询范围上限,n为查询次数
    	int m,n,c;
    	// [5] 输入查询范围上限m和查询次数n
    	cin>>m>>n;
    	// [6] 调用线性筛函数生成1~m范围内的所有素数
    	MakePrime(m);
    	// [7] 循环读取n次查询的k值,存入arr数组
    	for(int i=0;i<n;i++){
    		cin>>arr[i]; 
    	}
    	// [8] 循环处理每个查询,输出第k小的素数(arr1索引为k-1,因为数组从0开始)
    	for(int i=0;i<n;i++){
    		printf("%d\n",arr1[arr[i]-1]);
    	}
    	return 0;
    }
    
    • 1

    信息

    ID
    1228
    时间
    1000ms
    内存
    512MiB
    难度
    2
    标签
    递交数
    7
    已通过
    1
    上传者