zoukankan      html  css  js  c++  java
  • GHOJ 129 桐桐的猜想

    题目描述

           今天,桐桐在复习素数的知识时,发现了有趣的现象,例如4=2+2,5=2+3,6=3+3,7=2+5等等,桐桐列举了很多数,都是这样,所以她大胆地得出了一个结论:任何一个不小于4的数都能表示成两个质数的和。你能找出一些反例,证明桐桐的结论是错误的吗?

     

    输入输出格式

    输入格式

           两行,第一行为一个整数n(1≤n≤50);接下来有n行,每行包含一个整数m。(3<=10^6)

     

    输出格式

            共n行,每行对应于每一个m,如果m不能表示成两个质数的和,则输出“NO WAY!”;否则输出一种方案。如果有多种可行方案,输出两个质数的差最大的那一种。

     

    输入输出样例

    输入样例

    2

    10

    11

     

    输出样例

    10=3+7

    NO WAY!

     

    题解

            一般人看到这题都是直接用筛法,事实上这个方法也可以。

    #include <iostream>
    #include <cstdio>
    #include <cmath>
    
    using namespace std;
    
    int m, n[55], maxn;
    int p[1000005];
    int a[100005], cnt;
    
    int main()
    {
        scanf("%d", &m);
        for(register int i = 1; i <= m; ++i)
        {
            scanf("%d", n + i);
            if(n[i] > maxn) maxn = n[i];
        }
        for(register int i = 2; i <= maxn; ++i)
        {
            if(!p[i]) a[++cnt] = i;
            for(register int j = 1; i * a[j] <= maxn; ++j)
            {
                p[i * a[j]] = 1;
                if(!(i % a[j])) break;
            }
        }
        int op;
        for(register int i = 1; i <= m; ++i)
        {
            op = 0;
            for(register int j = 1; a[j] <= n[i] - a[j]; ++j)
            {
                if(!p[n[i] - a[j]])
                {
                    printf("%d=%d+%d
    ", n[i], a[j], n[i] - a[j]);
                    op = 1;
                    break;
                }
            }
            if(!op) printf("NO WAY!
    ");
        }
        return 0;
    }
    参考程序1

            但实际上这题,其实当m为偶数时是强哥德巴赫猜想,当m为奇数时,应该等于奇数加偶数,而偶数质数只有2,所以就能转换成当m为奇数时,判断m-2是否为质数

    #include <iostream>
    #include <cstdio>
    #include <cmath>
    
    using namespace std;
    
    int m, n[55], maxn;
    int p[1000005];
    int a[100005], cnt;
    
    int main()
    {
        scanf("%d", &m);
        for(register int i = 1; i <= m; ++i)
        {
            scanf("%d", n + i);
            if(n[i] > maxn) maxn = n[i];
        }
        int srmaxn = sqrt(maxn);
        a[++cnt] = 2;
        for(register int i = 4; i <= maxn; i += 2)
        {
            p[i] = 1;
        }
        for(register int i = 3; i <= srmaxn; i += 2)
        {
            if(p[i]) continue;
            a[++cnt] = i;
            for(register int j = i + i; j <= maxn; j += i)
            {
                p[j] = 1;
            }
        }
        for(register int i = 1; i <= m; ++i)
        {
            if(n[i] & 1)
            {
                if(p[n[i] - 2]) printf("NO WAY!
    ");
                else printf("%d=2+%d
    ", n[i], n[i] - 2);
            }
            else
            {
                // 哥德巴赫猜想
                for(register int j = 1; ; ++j)
                {
                    if(!p[n[i] - a[j]])
                    {
                        printf("%d=%d+%d
    ", n[i], a[j], n[i] - a[j]);
                        break;
                    }
                }
            }
        }
        return 0;
    }
    参考程序2

           到现在之后,其实这个程序还有优化的地方。

           题目中给的n很小,我们可以把筛法缩减,然后后面暴力判断质数即可,这样就可以做到0ms了。所以合理分析时间复杂度还是很重要的。(懒得发程序了)

  • 相关阅读:
    widget的进一步使用,利用AppWidgetProvider实现桌面的时钟挂件
    opengl绘图,画一个旋转的四边形和一个旋转的三角形,平滑着色和单一着色
    opengl se画图
    绘制立方体和单个的矩阵,并映射纹理图像
    opengl的坐标和glFrustumf的设定及参数相关意义
    glDrawElements 和glDrawArrays
    spring mvc的拦截器
    spring mvc 文件上传
    spring mvc返回json字符串的方式
    springmvc的数据校验
  • 原文地址:https://www.cnblogs.com/kcn999/p/10343501.html
Copyright © 2011-2022 走看看