【问题标题】:Trying to find the 10001st prime number, c#试图找到第 10001 个素数,c#
【发布时间】:2018-12-29 15:42:33
【问题描述】:

我正在尝试“找到第 10001 个素数”作为 Project Euler 挑战的一部分,但我不知道为什么我的代码不起作用。当我测试我的 isPrime() 函数时,它成功地找到了一个数字是否是素数,但我的程序返回 10200 作为第 10001 个素数。这是为什么呢?

这是我的代码:

using System;
using System.Collections.Generic;

namespace Challenge_7
{
    class Program
    {
        static void Main(string[] args)
        {
            Console.WriteLine("Solution to Project Euler");
            Console.WriteLine("Challenge 7 - Find the 10001st prime");

            Console.WriteLine("\nProject Start:");

            List<int> primes = new List<int>();

            int number = 1;
            while (primes.Count != 10001)
            {
                if (isPrime(number))
                {
                    primes.Add(number);
                    Console.WriteLine(number);
                }

                number++;
            }

            Console.WriteLine("The 10001st prime is: {0}", primes[10000]);

            Console.ReadLine();
        }

        private static bool isPrime(int n)
        {
            bool prime = true;

            for (int i = 1; i <= Math.Ceiling(Math.Sqrt(n)); i++)
            {
                for (int j = 1; j <= Math.Ceiling(Math.Sqrt(n)); j++)
                {
                    if (i * j == n)
                    {
                        prime = false;
                    }
                }
            }
            return prime;
        }
    }
}

【问题讨论】:

  • 所以如果你调用 isPrime(10200) 你是真的吗?
  • 正如彼得在答案中提到的,您的方法不正确。有很多方法可以检查 SOF 上的数字是否为素数。我建议你学习并尝试这个:stackoverflow.com/a/15743238/4329813
  • 您使用Math.Sqrt() 的方法应仅适用于检查i * j == n 的一个号码,而不适用于两个值。
  • Sqrt(10200) is 100.99510200 = 2 * 5100 但您的 for loop 永远不会到达 5100 以检查 2 * 5100

标签: c# primes


【解决方案1】:

这里有一个提示::

想象一个数字是 3 个素数的乘积。 比方说 3、5 和 7(或)105;

sqrt(105) == 10.2 所以上限是 11

没有两个小于 11 的数字乘以 105。 所以你的算法会错误地返回真!

再试一次! :-D

【讨论】:

    【解决方案2】:

    问题在于你的循环。 Math.Ceiling(Math.Sqrt(10200))101 并且您需要检查 102 * 100 = 10200 但您的循环永远不会到达 102 并返回 10200 作为素数!

    您可以将下面的代码用于isPrime。它存在于this link 中,我为你改成了 C#:

    private static bool isPrime(int n)
    {
        if (n <= 1)
            return false;
        else if (n <= 3)
            return true;
        else if (n % 2 == 0 || n % 3 == 0)
            return false;
        int i = 5;
        while (i * i <= n)
        {
            if (n % i == 0 || n % (i + 2) == 0)
                return false;
            i += 6;
        }
        return true;
    }
    

    【讨论】:

      【解决方案3】:
      using System;
      using System.Collections.Generic;
      using System.Linq;
      using System.Text;
      using System.Threading.Tasks;
      
      namespace nthPrimeNumber
      {
          class Program
          {
              static void Main(string[] args)
              {
                  ulong starting_number = 1;
                  ulong last_number = 200000; //only this value needs adjustment
                  ulong nth_primenumber = 0;
                  ulong a;
                  ulong b;
                  ulong c;
                  for (a = starting_number; a <= last_number; a++)
                  {
                      b = Convert.ToUInt64(Math.Ceiling(Math.Sqrt(a)));
                      for (c = 2; c <= b; c++)
                      {
                          if (a == 1 || (a % c == 0 && c != b))
                          {
                              break;
                          }
                          else
                          {
                              if (c == b)
                              {
                                  nth_primenumber = nth_primenumber + 1;
                                  break;
                              }
                          }
                      }
                      if (nth_primenumber == 10001)
                      {
                          break;
                      }
                  }
                  Console.WriteLine(nth_primenumber + "st" + "prime number is " + a);
                  Console.ReadKey();
              }
          }
      }
      

      上面的程序生成 1 到 200000 之间的素数。程序计算生成的素数并检查生成的素数是否已经是 10001。程序打印第 10001 个素数。如果程序在控制台中没有显示第 10001st(或显示低于 10001),那是因为 last_number 的值很小——然后尝试调整 last_number 的值(让它变大)。在这个程序中,我已经调整了 last_number 的值,将打印第 10001 个素数。

      【讨论】:

      • 嗨,John,在您的答案中包含解释会很有帮助,而不仅仅是代码。这样一来,人们就更容易从答案中学习并理解为什么该代码可以解决他们的问题。
      猜你喜欢
      • 1970-01-01
      • 2016-09-15
      • 2015-11-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-01-22
      相关资源
      最近更新 更多