Хотел написать программу по заданию, но, как оказалось, в который раз я попытался решить практически неразрешимую задачу. Всё никак не мог достичь приемлемой скорости вычислений… Ещё бы. Общее количество делителей заданного числа оказалось равным 2963520000.
Сообщение от Mike_Boone
и так работает
Работает, конечно. Только считать будет до скончания веков. Или, если переполнение BigInteger аварийно завершает программу, то до момента переполнения переменной i. Если добавить условие окончания нахождения делителей, то выводить все делители на экран программа будет где-то пару лет.
Сообщение от Artyom2124
Найти все делители
Artyom2124, Вы уверены? Если программа будет выдавать по 1000 делителей в секунду, она будет работать более месяца, и, если делители записывать в текстовый файл, конечный объём файла будет примерно 160 гигабайт (более 170000000000 символов). Сильно сомневаюсь, что такое задание могли дать в каком-либо учебном заведении.
Artyom2124, может быть, нужно найти все простые делители?
Это я сделал. К счастью, максимальный простой делитель Вашего числа сравнительно маленький, и помещается в тип integer. Общее количество делителей числа не помещается в тип integer, для подсчёта указанной величины я использовал тип real.
Программа факторизации Вашего числа, находит все простые делители, их максимальные степени и общее количество делителей числа:
Pascal | ||
|
На моём древнем ноутбуке в Pascal ABC программа считает примерно 24 секунды, эта же программа, подрихтованная и запущенная в Free Pascal, считает примерно 4 секунды.
Код
Prime divisors: +----+---------+-----------+ | # | divisor | max power | +----+---------+-----------+ | 1 | 1297 | 6 | | 2 | 5651 | 2 | | 3 | 6959 | 5 | | 4 | 10799 | 2 | | 5 | 12547 | 1 | | 6 | 15161 | 4 | | 7 | 16223 | 1 | | 8 | 16417 | 4 | | 9 | 17681 | 4 | | 10 | 18541 | 4 | | 11 | 20411 | 6 | | 12 | 23563 | 6 | | 13 | 26591 | 7 | | 14 | 27943 | 1 | | 15 | 28513 | 3 | +----+---------+-----------+ Total quantity of all divisors = 2963520000
Первая колонка — номер простого делителя, вторая — величина простого делителя, третья — максимальная степень, при возведении в которую простого делителя, получившееся число всё ещё делит исходное число нацело.
Ниже таблицы — общее количество всех делителей.
Пояснения по количеству делителей: любой делитель числа может быть представлен в виде произведения степеней всех простых делителей числа, степень при конкретном простом делителе может быть от 0 до упомянутой выше максимальной степени. Таким образом, общее количество делителей равно количеству всех возможных комбинаций степеней при всех простых делителях, иными словами, произведению увеличенных на 1 максимальных степеней для каждого простого делителя.
Напоследок, если строго по заданию… Казалось бы, имеет смысл дописать мою программу… Осталось совсем немного: перебрать все степени при простых делителях, и умножить исходную единицу нужное количество раз на каждый простой делитель, и так 2963520000 раз… Короче, сущий пустяк, думаю, за год можно будет найти все делители заданного числа.
Добавлено через 2 часа 3 минуты
Если желаете, можете
Сообщение от Artyom2124
найти как можно больше положительных делителей заданного числа
хоть вручную. Сначала принимаете все степени равными 0, и получаете первый делитель:
285130279430265910235630204110185410176810164170162230151610125470107990695905651012970
=1
Затем начинаем увеличивать степени, например, в порядке справа налево, и перебираем все возможные комбинации следующим образом: если степень в самом правом сомножителе достигла максимальной по таблице, то обнуляем эту степень, и увеличиваем следующую (вторую справа), и продолжаем в том же духе до тех пор, пока не переполнится и вторая справа степень, тогда увеличиваем третью справа, а вторую справа обнуляем, и так до тех пор, пока набор степеней не будет такой же, как в таблице:
285130279430265910235630204110185410176810164170162230151610125470107990695905651012971
=1297
285130279430265910235630204110185410176810164170162230151610125470107990695905651012972
=1682209
285130279430265910235630204110185410176810164170162230151610125470107990695905651012973
=2181825073
285130279430265910235630204110185410176810164170162230151610125470107990695905651012974
=2829827119681
285130279430265910235630204110185410176810164170162230151610125470107990695905651012975
=3670285774226257
285130279430265910235630204110185410176810164170162230151610125470107990695905651012976
=4760360649171455329
285130279430265910235630204110185410176810164170162230151610125470107990695905651112970
=5651
285130279430265910235630204110185410176810164170162230151610125470107990695905651112971
=7329347
…
285130279430265910235630204110185410176810164170162230151610125470107990695905651112976
=26900798028467894064179
285130279430265910235630204110185410176810164170162230151610125470107990695905651212970
=31933801
…
285130279430265910235630204110185410176810164170162230151610125470107990695905651212976
=152016409658872069356675529
285130279430265910235630204110185410176810164170162230151610125470107990695915651012970
=6959
…
285130279430265910235630204110185410176810164170162230151610125470107990695915651212976
=1057882194816090730653105006311
…
285133279431265917235636204116185414176814164174162231151614125471107992695955651212976
=1967084231266765692860010223558507897047170146058053492025445758905635912540900 79162973668806152370560989633700137089767703775820200092605536123071613442454080 946743909994972297960260325884838413934893551073244410428771253965567859
Добавлено через 4 часа 36 минут
Хотя… Если применить что-нибудь получше строк, то… Программа на Free Pascal Compiler для печати заданного количества делителей, начиная с делителя с заданным номером:
Pascal | ||
|
Делитель числа размещается в массиве, который используется в качестве 17-разрядного длинного числа в 100000000000000-ричной системе счисления. Так как основание системы счисления является степенью числа 10, то перевести такое число в десятичное не вызывает никаких проблем. Большее основание системы счисления применить не получилось из-за целочисленного переполнения.
В программе нет проверки вводимых значений.
можно объединить обе программы.
Можно переделать для вывода делителей в файл.
Можно переделать под Pascal ABC, но неохота из-за танцев с бубном ввиду отсутствия в Pascal ABC достаточно ёмкого целочисленного типа.
Проверить программу очень просто: нужно ввести Start number: 2963520000 и Count: 1, и будет напечатан последний делитель заданного числа, а именно, само заданное число.
0
Пример программы паскаль, которая находит все делители натурального числа и их сумму
Итак, продолжаю выкладывать наиболее востребованные исходники Паскаль ABC по теме циклы паскаль (FOR). Задача Pascal такая: Дано натуральное число. Найти все его делители и их сумму. Число вводится с клавиатуры, делители выводятся через пробелы, сумма в следующей строке. Допустим диалог с пользователем.
Исходный код программы:
Var n, i, sum: integer; //Описание переменных
Begin //Начло программы
writeln ('Введите число'); //Диалог с пользователем
readln(n); //Считывание числа
sum := n; //Присваивание сумме значение самого числа (само число - уже делитель самого себя)
writeln('Делители числа:'); //Диалог с пользователем
for i := 1 to n div 2 do //Цикл For от до половины n
if (n mod i) = 0 then begin //Если число делится на i, то выводим
write(i,' ');
sum := sum + i; //К значению суммы прибавляем делитель
end; //Конец условного оператора if
writeln(n); //Вывод самого числа, т.к. оно тоже делитель
writeln('Сумма делителей: ',sum); //Вывод суммы делителей
End. //Конец программы
Дата: 2013-06-25 10:53:19 Просмотров: 48719
Теги: Паскаль Pascal исходник исходники скачать FOR циклы
Введение.
Итак, я продолжаю решать самые популярные и самые распространенные задачи на языке программирования PascalABC с использованием циклов FOR, на этот раз это задача на нахождение делителей числа и их суммы.
Задача.
Дано
натуральное число X, наша задача — найти его делители и их сумму SUMMA. Число X считывается с клавиатуры, делители выводятся на экран через знак пробела, а их сумма SUMMA располагается в следующей строке. Решим поставленную перед нами задачу с использованием цикла FOR, добавляя к каждой строке необходимые пояснения для абсолютного понимания алгоритма.
Код.
Var n, i, sum: integer; //Описание переменных
Begin //Начло программы
writeln (‘Введите число’); //Диалог с пользователем
readln(n); //Считывание числа
sum := n; //Присваивание сумме значение самого числа (само число — уже делитель самого себя)
writeln(‘Делители числа:’); //Диалог с пользователем
for i := 1 to n div 2 do //Цикл For от до половины n
if (n mod i) = 0 then begin //Если число делится на i, то выводим
write(i,’ ‘);
sum := sum + i; //К значению суммы прибавляем делитель
end; //Конец условного оператора if
writeln(n); //Вывод самого числа, т.к. оно тоже делитель
writeln(‘Сумма делителей: ‘,sum); //Вывод суммы делителей
End. //Конец программы
Натурáльные чи́сла (от лат.naturalis «естественный») — числа, возникающие естественным образом при счёте (1, 2, 3, 4, 5, 6, 7 и так далее…). Последовательность всех натуральных чисел, расположенных в порядке возрастания, называется натуральным рядом.
Ниже рассмотрен пример поиска всех делителей натурального числа на Pascal.
var a,n,c,d:word; begin readln( a ); n:=1; while ( n <= sqrt(a) ) do begin c:=a mod n; d:=a div n; if c = 0 then begin writeln( n ); if n <> d then writeln( d ); end; inc( n ); end; end.
Program
pr32 (Input, Output);
Объявление
имени программы
Var
Блок
объявления глобальных переменных
N
: Integer;
Переменная
N — заданное число
i
: Integer;
Переменная
i — параметр цикла и делитель
Begin
Начало
тела программы
WriteLn
(‘PASCAL: Нахождения всех делителей
заданного числа.’);
Формулировка
цели алгоритма
Write
(‘Введите число, для которого ищутся
делители: ‘);
Запрос
N — числа, для которого ищутся делители
ReadLn
(N);
Ввод
N
WriteLn
(‘Делители числа N = ‘, N, ‘ равны:’);
Сообщение
пользователю о выводе найденных
делителей
For
i := 1 To N Do
Цикл
для i от 1 до N нахождения делителей числа
N
If
(N Div i) = (N / i) Если
целая часть дроби N/i равна дроби N/i,
Проверка
равенства кратности числа N делителю i
Then
WriteLn (i);
i является очередным делителем числа
N
В
случае кратности выводим очередной
делитель — число i
ReadLn;
Ожидание
нажатия клавиши Enter для завершения
End.
Конец
программы