C++ вопрос о простых числах

Я пытаюсь сделать программу, которая определяет, является ли число простым или составным. Я дошел до сих пор. Не могли бы вы дать мне какие-либо идеи, чтобы это сработало? Однако все простые числа будут , поскольку составные имеют значения, которые равны как r>0, так и r==0, они всегда будут классифицироваться как простые. Как я могу это исправить?

int main()
{
    int pNumber, limit, x, r;               
    limit = 2;
    x = 2;

    cout << "Please enter any positive integer: " ;
    cin >> pNumber;

    if (pNumber < 0)
    {
        cout << "Invalid. Negative Number. " << endl;
        return 0;
    }
    else if (pNumber == 0)
    {   
        cout << "Invalid. Zero has an infinite number of divisors, and therefore neither composite nor prime." << endl;
        return 0;
    }
    else if (pNumber == 1)
    {
        cout << "Valid. However, one is neither prime nor composite" << endl;
        return 0;
    }
    else
    {
        while (limit < pNumber)
        {
            r = pNumber % x;
            x++;
            limit++;

            if (r > 0)
                cout << "Your number is prime" << endl;
            else 
            {
                cout << "Your number is composite" << endl;
                return 0;
            }
        }
    }

    return 0;
}

person Sagistic    schedule 08.03.2010    source источник
comment
Возможно, вы захотите сразу же добавить проверку четных чисел, чтобы ускорить процесс, например, if( num % 2 == 0), тогда ваш цикл будет увеличиваться на двойки, а не на единицы. Кроме того, есть много изящных приемов для нахождения простых чисел, 5 довольно легко, так как число заканчивается на 0 или 5, числа, делящиеся на 3, имеют цифры, которые при суммировании делятся на 3. Лучше всего было бы исключить действительно легко проверить сначала.   -  person Maynza    schedule 08.03.2010
comment
@Maynza Числа на самом деле не заканчиваются на 5. Просто их десятичное представление заканчивается на «5». Чтобы использовать такую ​​проверку, вам нужно сначала преобразовать целое число в строку или каким-то образом составить список его цифр. В этом случае вы можете получить пользовательский ввод в виде строки, выполнить эти две проверки, а затем преобразовать их в целое число для всех остальных проверок. Но это больше работы, и я не знаю, будет ли это быстрее.   -  person MatrixFrog    schedule 08.03.2010
comment
Нет, просто проверьте (num % 10 == 5).   -  person Maynza    schedule 08.03.2010
comment
вместо while (limit ‹ pNumber) используйте while (limit ‹= std::sqrt(pNumber)+1)   -  person    schedule 08.03.2010
comment
@Maynza: ты забыл || num % 10 == 0. Или будь умнее и напиши, что ты имел в виду на самом деле: num % 5 ==0 . Это совсем не хитрый трюк. Это также работает для num % 37 == 0 и num % 600000001 == 0   -  person MSalters    schedule 08.03.2010
comment
@MSalters: Вы правы, но на самом деле вы ничему не научитесь, если будете делать это таким образом, я просто думаю, что интересно анализировать числа и видеть, как появляются определенные закономерности.   -  person Maynza    schedule 08.03.2010
comment
@Maynza: проблема в том, что в числах есть реальные закономерности, но они в двоичном формате. Например. есть отличный трюк для проверки деления на 11. Это работает для всех значений 11;) - как двоичных 11, так и десятичных 11. Он включает в себя суммирование всех цифр в нечетном и четном положении и проверку, равны ли они по модулю 11 , например 1001 делится, потому что 1=1. (на всех базах!)   -  person MSalters    schedule 08.03.2010


Ответы (7)


Ознакомьтесь с http://en.wikipedia.org/wiki/Prime_number и http://en.wikipedia.org/wiki/Primality_test

Простейший тест на простоту выглядит следующим образом: по входному числу n проверьте, делится ли любое целое число m от 2 до n − 1 на n. Если n делится на любое m, то n составное, в противном случае оно простое.

person Pierre-Antoine LaFayette    schedule 08.03.2010
comment
Вам нужно только проверить sqrt(n). - person Maynza; 08.03.2010
comment
Самый простой. Согласованный. Но сложность можно значительно уменьшить, используя детерминированную проверку простоты Миллера-Рабина. - person N 1.1; 08.03.2010
comment
@nvl: тестируемое число — int. Миллер-Рабин - это огромное излишество, и я не уверен, что он еще быстрее на 32-битном int. Алгоритм, правильность которого опирается на гипотезу Римана, вряд ли стоит упоминать тому, кто изо всех сил пытается правильно написать свой первый тест на простоту ;-) - person Steve Jessop; 08.03.2010
comment
@steve jessop: хм, может быть :). По крайней мере, он должен знать, что простые числа имеют вид 6k+1, 6k-1. (~ 2,3) - person N 1.1; 08.03.2010

что касается вашего кода, вы не проверяли, введу ли я 2, что произойдет, а также вы ничего не вернули, если это простое число... вот почему оно всегда возвращает простое число, несмотря на то, что число составное. вот код ниже =>

#include<iostream>
using namespace std;
int main(){
    int pNumber, limit, x, r;               
    limit = 2;
    x = 2;

    cout << "Please enter any positive integer: " ;
    cin >> pNumber;

    if (pNumber < 0){
        cout << "Invalid. Negative Number. " << endl;
        return 0;
    }
    else if (pNumber == 0){   
        cout << "Invalid. Zero has an infinite number of divisors, and therefore neither composite nor prime." << endl;
        return 0;
    }
    else if (pNumber == 1){
        cout << "Valid. However, one is neither prime nor composite" << endl;
        return 0;
    }
    else if (pNumber == 2){
        cout << " Your number is prime" << endl;
        return 0;
    }
    else{
        while (limit < pNumber){
            r = pNumber % x;
            x++;
            limit++;

            if (r > 0){
                cout << "Your number is prime" << endl;
                return 0;
            }
            else{
                cout << "Your number is composite" << endl;
                return 0;
            }
        }
    }
    return 0;
}
person Saikat Kundu    schedule 28.11.2015

Во-первых, вам захочется вырваться из цикла, когда вы найдете x, где pNumber % x == 0. Все, что вам нужно сделать, это найти один множитель pNumber больше 1 и меньше pNumber, чтобы доказать, что он не является простым — нет смысла искать дальше. Если вы прошли весь путь до x = pNumber, не найдя ни одного, то вы знаете, что pNumber — простое число. На самом деле, даже если вы доберетесь до квадратного корня из pNumber, не найдя ни одного, это простое число, поскольку, если оно имеет множитель больше этого, оно должно иметь множитель меньше этого. Есть смысл?

person Tim Goodman    schedule 08.03.2010
comment
Ключевым моментом является то, что у вас есть правильное представление о том, что r==0 показывает вам, что это не простое число. . . но если вы не остановитесь, когда найдете какое-то r==0, а вместо этого продолжите работу и перезапишете его каким-нибудь r!=0, то вы отбросите доказательство того, что оно не простое, и ошибочно пометите его как простое. - person Tim Goodman; 08.03.2010
comment
да, у меня проблемы с остановкой. Как я могу сломаться на этом. - person Sagistic; 08.03.2010
comment
Вы почти ответили на свой вопрос. Найдите ключевое слово break. - person MatrixFrog; 08.03.2010
comment
лол, я знаю, что ты должен использовать перерыв, однако я не уверен, как это сделать. Я отредактировал скрипт, но теперь он объявляет все простые числа b4 и говорит вам, что это составной. ржу не могу - person Sagistic; 08.03.2010
comment
Строка, в которой вы указываете cout‹‹Prime, используется каждый раз, когда r > 0, что не обязательно означает, что оно простое, но число, на которое вы пытаетесь его разделить, не идет поровну. - person Maynza; 08.03.2010
comment
да, поэтому, когда я ввожу число, например 13, оно отобразит, что ваше число является простым 12 раз .. ха-ха .. позвольте мне попытаться это исправить - person Sagistic; 08.03.2010

Я не знаю, чему вас учили до сих пор, но мой учитель дискретной математики был поклонником Тест Миллера-Рабина. Это довольно точный тест, который очень легко закодировать, в нескольких базовых тестах у вас есть очень незначительный шанс, что у вас есть Номер Кармайкла. Если вы не продвинулись так далеко в своих исследованиях, я бы просто придерживался некоторых основных правил деления чисел.

person Maynza    schedule 08.03.2010

Простейший метод для заданного числа n , если оно полностью делится на любое число от 2 до sqrt (n), это составное или простое число.

person Kazoom    schedule 08.03.2010

Привет, я сделал это также без использования заголовочного файла math.h .... Использовал компилятор turboc. Следующая программа проверяет, является ли число простым или составным.

                   #include<iostream.h>
                   #include<conio.h>
                   class prime
                             {
                                int a;
                                public:
                                     void check();

                             };
                             void prime::check()
                                                 {
                                                      cout<<"Insert a number";
                                                      cin>>a;
                                                      int count=0;
                                                      for(int i=a;i>=1;i--)
                                                         {
                                                            if(a%i==0)
                                                                    {
                                                                      count++;
                                                                     }
                                                         }
                                                             if(count==1)
                                                                      {
                                      cout<<"\nOne is neither prime nor composite";
                                                                       }
                                                             if(count>2)
                                                                       {
                                      cout<<"\nThe number is composite " ;
                                                                       }
                                                             if(count==2)
                                                                       {
                                      cout<<"\nThe numner is prime";
                                                                       }
                                 }

                                void main()
                                          {
                                            clrscr();
                                            prime k;
                                            k.check();
                                            getch();
                                          }
person Deepeshkumar    schedule 29.10.2012

person    schedule
comment
Эта функция считает 4, 8 и 10 простыми числами. - person M Perry; 08.03.2010
comment
@M Перри: ой, вот что я получаю за ввод кода без его тестирования. Я пропустил набор скобок (теперь исправлено). Спасибо, что указали на это. - person Jerry Coffin; 08.03.2010
comment
Он также считает, что 1 — простое число, но любой, кто передает 1 на проверку на простоту, вероятно, заслуживает того, что получает. - person Steve Jessop; 08.03.2010
comment
@Steve: Возврат логического значения ограничивает нас ответом да / нет, а для 1 на самом деле его нет - для некоторых целей удобно рассматривать его как простое число, другие как составные, а третьи как ни одно. Ни один из них не является наиболее распространенным, но едва ли единственным ответом. - person Jerry Coffin; 08.03.2010
comment
Вот что я имею в виду под словами «заслуживают того, что получают». Это немного похоже на вопрос, начинаются ли натуральные числа с 0 или с 1. Однако у меня есть математическое образование, так что меня научили тому, что 1 не является простым. Это делает определение простого числа длиннее, а формулировку основной теоремы арифметики короче. Насколько я помню, я никогда не видел, чтобы 1 был составным. В теории колец есть понятие единиц, которые явно исключены из числа простых или неприводимых. Однако эта концепция почти вырождена для целых чисел, поскольку есть только две единицы (1 и -1). - person Steve Jessop; 08.03.2010