首页 > 其他分享 >【洛谷P1036】 [NOIP2002 普及组] 选数

【洛谷P1036】 [NOIP2002 普及组] 选数

时间:2024-03-31 13:04:59浏览次数:29  
标签:12 洛谷 int 选数 sum P1036 19 素数 整除

一、题目:

二、解题思路:

本文章采用的解决方法是递归与DFS(深度优先搜索)。

以下图是思路图:

1.首先-确定位置

题目说4个数字取三个数,所以考虑的只有三个位置和这三个位置分别放什么数值。从第一个位置开始放数。

2.其次-开始放数

分为4种可能,第一位置可以先放3,那么第二个位置就只能放7,12,19这三个数字任意一个数字了,假设放了7,那么第三个位置就只能放12或19。所以本次得到的结果是3 7 12或3 7 19.(这里只谈的简单思路,编写代码的或者写类似搜索题要注意回溯问题和恢复现场)。接着再继续列举其他可能性,得到最后结果为3 7 12,3 7 19,3 12 19,7 12 19这四种结果,发现与题目给的样例一致。

3.最后-考虑素数如何判断

素数是指只能被1和它自身整除的大于1的自然数。因此,判断一个数是否为素数,需要满足以下几个条件:

  1. 大于1的自然数:素数必须大于1,因为1不是素数。同时,它必须是自然数,即非负整数。

  2. 只有1和自身两个正因数:这是素数最核心的定义。也就是说,除了1和它本身以外,没有其他正整数能够整除它。如果一个数有除了1和它本身以外的其他正因数,那么它就不是素数。

素数(质数)的判断:检查该数是否能被比它小的任何正整数整除。如果能被整除,则它不是素数;如果不能被任何比它小的正整数整除,则它是素数。

步骤如下:

  • 排除小于等于1的数:任何小于等于1的数都不是素数。
  • 排除偶数:除了2以外,所有的偶数都不是素数,因为它们都可以被2整除。
  • 检查奇数因子:从3开始,到被检测数的平方根为止,检查是否能被这些奇数整除。如果能被整除,则不是素数;如果不能被整除,则继续检查下一个奇数。
  • 达到平方根即可停止:如果一个数有一个大于它平方根的因子,那么它必然还有一个小于或等于其平方根的因子。因此,我们只需要检查到被检测数的平方根即可。

三、分步骤-实现代码

1.先设置好全局变量

#include<iostream>
using namespace std;

const int N = 30;
int arr[N];//存答案
int q[N];//存数据
int n,k;
int res;//保存题目要求的种类数

2.主函数

1)for循环用来给数组赋值

2)函数传参-当前枚举到哪个位置,从第一个位置开始

int main()
{
    scanf("%d %d",&n,&k);
    for(int i = 1; i <= n; i++)
    {
        scanf("%d",&q[i]);
    }
    
    dfs(1,1);
    
    printf("%d\n",res);
    
    return 0;
}

3.开始遍历

利用for循环遍历

void dfs(int x, int start)//x表示当前到了哪个位置,start表示从几开始枚举
{
    //选谁
    for(int i = start; i <= n; i++){
        arr[x] = q[i];
        dfs(x + 1 , i + 1);//深度优先 继续向下
        arr[x] = 0;//恢复现场
    }
}

 遍历完所有数字以后开始求出总和,并进行判断是否为素数

if(x > k)
    {
        int sum = 0;
        for(int i =1; i <= k; i++){
            sum = sum + arr[i];
        }
        
        //prime number意思是素数
        if(is_prime(sum)){
            res++;
        }
        return ;
    }
    

4.素数判断

bool is_prime(int sum){
    if(sum < 2) return false;
    for(int i = 2; i <= sum / i; i++){//如果写成i*i<=sum,数据大的时,可能会爆出int的最大范围,此处还可以写成i<=sqrt(sum)
        if(sum%i==0)
        {
            return false;
        }
    }
    return true;//此处有好几处判断以后才能返回true,易错点在if判断完以后用else return true.这样写就错了
}

四、最终代码

#include<iostream>
using namespace std;

const int N = 30;
int arr[N];//存答案
int q[N];//存数据
int n,k;
int res;//保存题目要求的种类数

bool is_prime(int sum){
    if(sum < 2) return false;
    for(int i = 2; i <= sum / i; i++){//如果写成i*i<=sum,数据大的时,可能会爆出int的最大范围,此处还可以写成i<=sqrt(sum)
        if(sum%i==0)
        {
            return false;
        }
    }
    return true;//此处有好几处判断以后才能返回true,易错点在if判断完以后用else return true.这样写就错了
}

void dfs(int x, int start)//x表示当前到了哪个位置,start表示从几开始枚举
{
    if(x > k)
    {
        int sum = 0;
        for(int i =1; i <= k; i++){
            sum = sum + arr[i];
        }
        
        //prime number意思是素数
        if(is_prime(sum)){
            res++;
        }
        return ;
    }
    
    //选谁
    for(int i = start; i <= n; i++){
        arr[x] = q[i];
        dfs(x + 1 , i + 1);//深度优先 继续向下
        arr[x] = 0;//恢复现场
    }
}

int main()
{
    scanf("%d %d",&n,&k);
    for(int i = 1; i <= n; i++)
    {
        scanf("%d",&q[i]);
    }
    
    dfs(1,1);
    
    printf("%d\n",res);
    
    return 0;
}

 

如果这篇文章有任何问题或建议请评论留言,看到了会及时解决

标签:12,洛谷,int,选数,sum,P1036,19,素数,整除
From: https://blog.csdn.net/2301_77055070/article/details/137196363

相关文章

  • 【洛谷】P1004 [NOIP2000提高组]方格取数
    题目描述题目描述设有N×N 的方格图(N≤9),我们将其中的某些方格中填入正整数,而其他的方格中则放入数字 0。如下图所示(见样例):某人从图的左上角的 A 点出发,可以向下行走,也可以向右走,直到到达右下角的 B 点。在走过的路上,他可以取走方格中的数(取走后的方格中将变为......
  • 洛谷题单指南-图的基本应用-P2853 [USACO06DEC] Cow Picnic S
    原题链接:https://www.luogu.com.cn/problem/P2853题意解读:找到所有奶牛都可以到达的牧场,就是要从奶牛所在位置开始遍历,求所有奶牛能重合的点的个数。解题思路:直接从从牛奶所在位置进行DFS,记录每个位置有奶牛能到的个数,个数等于奶牛总数的即合适的牧场。100分代码:#include<bi......
  • 洛谷题单指南-图的基本应用-P1127 词链
    原题链接:https://www.luogu.com.cn/problem/P1127题意解读:按字典序排列单词,使得相邻单词的首位字母一样。解题思路:由于单词之间可以相邻的条件是前一个单词的末尾字母和后一个单词的开头字母一样,因此可以遍历每一个单词,再找到每一个可以接在其后面的单词,建立一个邻接表,然后从......
  • 【洛谷】P1060 开心的金明
    P1049装箱问题确认所需算法题目链接:P1060开心的金明这题是一道01背包问题,如果你还不知道什么是背包问题,那么请看我的背包问题学习笔记思路这道题的输入有一点点奇怪,v[i]=2~n+1行的第一个数*第二个数。其他的稍微抽象一点就可以变为标准的01背包问题了。关于状态转移方程......
  • 【洛谷】P1049 装箱问题
    P1049装箱问题确认所需算法题目链接:P1049装箱问题通过看标签得知这题是一道背包问题,如果你还不知道什么是背包问题,那么请看我这篇文章既然我们知道了这道题是一道背包问题,那么下一步我们要确认他是01背包还是完全背包。首先我们回顾01背包和完全背包的区别:通过题意可知,每......
  • 【洛谷】 P1006 [NOIP2008提高组]传纸条
    题目描述小渊和小轩是好朋友也是同班同学,他们在一起总有谈不完的话题。一次素质拓展活动中,班上同学安排坐成一个 m 行 n 列的矩阵,而小渊和小轩被安排在矩阵对角线的两端,因此,他们就无法直接交谈了。幸运的是,他们可以通过传纸条来进行交流。纸条要经由许多同学传到对方手里,......
  • 洛谷1803
    P1803凌乱的yyy/线段覆盖-洛谷|计算机科学教育新生态(luogu.com.cn)所需知识:贪心本来还想用dfsbfs搜索来一点一点做的,看到了大佬的思路之后,直接orz了整体思路:因为要想尽可能的多参加比赛,所以越早结束比赛对后面留出来的时间就更多,可以参加更多场比赛,所以直接将每场......
  • 【洛谷 P8738】[蓝桥杯 2020 国 C] 天干地支 题解(字符串+数学+模运算)
    [蓝桥杯2020国C]天干地支题目描述古代中国使用天干地支来记录当前的年份。天干一共有十个,分别为:甲(jiǎ)、乙(yǐ)、丙(bǐng)、丁(dīng)、戊(wù)、己(jǐ)、庚(gēng)、辛(xīn)、壬(rén)、癸(guǐ)。地支一共有十二个,分别为:子(zǐ)、丑(chǒu)、寅(yín)、卯(mǎo)、辰(chén)、巳(sì)、午(wǔ......
  • 【洛谷 P8654】[蓝桥杯 2017 国 C] 合根植物 题解(并查集)
    [蓝桥杯2017国C]合根植物题目描述w星球的一个种植园,被分成m×nm\timesnm×n个小格子(东西方向......
  • 蓝桥杯 2022 省A 选数异或
    一种比较无脑暴力点的方法,时间复杂度是(n²+m)。(注意==的优先级比^高,记得加括号(a[i]^a[j])==x)#include<iostream>#include<vector>#include<bits/stdc++.h>//包含一些C++标准库中未包含的特定实现的函数的头文件usingnamespacestd;intmain(){intn,......