zoukankan      html  css  js  c++  java
  • NOIP 2002 选数

    洛谷 P1036 选数

    洛谷传送门

    JDOJ 1297: [NOIP2002]选数 T2

    JDOJ传送门

    Description

    ​ 已知 n 个整数 x1,x2,…,xn,以及一个整数 k(k<n)。从 n 个整数中任选 k 个整数相加,可分别得到一系列的和。例如当 n=4,k=3,4 个整数分别为 3,7,12,19 时,可得全部的组合与它们的和为:  

    3+7+12=22  

    3+7+19=29  

    7+12+19=38  

    3+12+19=34。  

    现在,要求你计算出和为素数共有多少种。  

    例如上例,只有一种的和为素数:3+7+19=29。

    Input

    n , k (1< =n< =20,k<n) x1,x2,…,xn (1< =xi< =5000000 )

    Output

    一个整数(满足条件的种数)。

    Sample Input

    4 3 3 7 12 19

    Sample Output

    1

    题解:

    本题考查的知识点:递归生成全排列,质数判断。

    递归生成全排列的相关知识:

    相关知识—全排列传送门

    相关知识—质数判断传送门

    思路:

    我们要枚举(n)数中(k)个数的全排列之和有多少是质数,需要生成全排列再判断一下质数即可,如果依次枚举无疑会超时,所以我们想出递归深搜来优化这个问题:

    我们搜索的时候需要维护这么几个参数:首先是还剩多少个数没有选进去,然后是已经选进去的和是多少,最后是剩下数字的选取范围。

    所以我们有如下的递归思路:

    假如k==0,说明我们已经有了一个全排列,这时候需要判断,否则,就进入选取环节:从start到end枚举递归深搜,累加和。这样就得到了我们要求的答案。

    代码:

    #include<cstdio>
    #include<cmath>
    using namespace std;
    int n,k;
    int a[21];
    bool check(int x)
    {
        for(int i=2;i<=sqrt(x);i++)
            if(x%i==0)
                return 0;
        return 1;
    }
    int dfs(int k,int sum,int start,int end)
    {
        if(k==0)
            return check(sum);
        int tot=0;
        for(int i=start;i<=end;i++)
            tot+=dfs(k-1,sum+a[i],i+1,end);
        return tot;
    }
    int main()
    {
        int n,k;
        scanf("%d%d",&n,&k);
        for(int i=1;i<=n;i++)
            scanf("%d",&a[i]);
        printf("%d",dfs(k,0,1,n));
        return 0;
    }
    
  • 相关阅读:
    String Kernel SVM
    基因组印记
    用Js的eval解析JSON中的注意点
    struts2中<s:select>标签的使用
    如何在Linux中使用cron命令
    怎样解决MySQL数据库主从复制延迟的问题
    PMON failed to acquire latch, see PMON dump
    java中对List中对象排序实现
    C语言typedef关键字
    企业级内部信息统一搜索解决方案
  • 原文地址:https://www.cnblogs.com/fusiwei/p/11357604.html
Copyright © 2011-2022 走看看