Описание задачи
Данная программа должна вывести все числа в заданном диапазоне, которые делились бы без остатка на определенное число.
Решение задачи
- На вход принимаются два числа, которые задают диапазон и записываются в разные переменные.
- Также принимается число, которое будет делителем.
- Используем цикл
for
, чтобы пройтись по всему диапазону и проверить все числа на кратность. Выводим только те числа, которые делятся на заданное число без остатка. - Конец.
Исходный код
Ниже дан исходный код для вывода всех чисел из заданного диапазона, которые удовлетворяют условию делимости на данное число. Результаты работы программы также даны ниже.
lower = int(input("Введите нижнюю границу диапазона:")) upper = int(input("Введите верхнюю границу диапазона:")) n = int(input("Введите делитель:")) for i in range(lower, upper + 1): if(i % n == 0): print(i)
Объяснение работы программы
- Пользователь вводит два числа, нижнюю и верхнюю границы. Они записываются в отдельные переменные.
- Далее пользователь вводит число, которое будет делителем. Оно также сохраняется в своей переменной.
- Значение переменной цикла
for
варьируется от нижней до верхней границы с шагом 1. - В процессе работы цикла проверяется, равен ли остаток от деления нулю. Если остаток равен нулю, делимое выводится на экран.
- Конец.
Результаты работы программы
Пример 1: Введите нижнюю границу диапазона:1 Введите верхнюю границу диапазона:50 Введите делитель:5 5 10 15 20 25 30 35 40 45 50 Пример 2: Введите нижнюю границу диапазона:50 Введите верхнюю границу диапазона:100 Введите делитель:7 56 63 70 77 84 91 98
Формулировка задачи:
Задача
Найдите количество чисел кратных k в отрезке [a, b]. Другими словами, вам нужно найти количество целых чисел x таких, что a ≤ x ≤ b и x делится на k.
Входные данные
В единственной строке входных данных находится три целых числа k, a, b (1 ≤ k ≤ 10^9; - 1018 ≤ a ≤ b ≤ 10^9).
Выходные данные
Выведите ответ на задачу.
Вопрос
Как пройти 57 тест программы?Никак не пойму.Я уже даже в строке #8 написал фигню, но это всё равно не работает :. Не понимаю, как обойти эти ошибки исполнения.
Код:
var a,b,x:Int64; k:byte; begin read(k,a,b); if ((k=1) and(a<0)) then x:=abs(a)+abs(b); if (a=-1000000000000000000) and (b= 1000000000000000000) then x:=b*2; if ((a=0) and (b=0)) then x:=1 else while (a<=b) do begin if (a mod k =0) then inc (x); inc(a); end; writeln(x); end.
Ввод:
1 -1000000000000000000 1000000000000000000
Вывод:
Ошибка выполнения [TIME_LIMIT_EXCEEDED]
Ошибка исполнения, код возврата -1
=====
Использовано: 10000 мс, 0 КБ
Код к задаче: «Найдите количество чисел кратных k в отрезке»
textual
var k, a, b, x: Int64; begin read(k, a, b); if a >= 0 then a := a + k - 1; a := a - a mod k; if b < 0 then b := b - k + 1; b := b - b mod k; x := ((b - a) div k) + 1; write(x) end.
Полезно ли:
5 голосов , оценка 3.800 из 5
Просмотров 2.3к. Обновлено 15 октября 2021
В диапазоне натуральных чисел от 2 до 99 определить, сколько из них кратны любому из чисел в диапазоне от 2 до 9.
Необходимо проверить кратность каждого числа сначала числу 2, потом 3 и т.д. до 9 включительно. Введем массив с восьмью ячейками. В первую будем записывать количество чисел кратных 2, во вторую — 3 и т.д.
- Записать в ячейки массива нули.
- Перебирая числа от 2 до 99,
- для каждого из них в цикле от 2 до 9
- проверять кратность числа внешнего цикла числу внутреннего.
- Если второе число делит нацело первое, значит увеличивать на 1 значение в соответствующей ячейке массива.
- для каждого из них в цикле от 2 до 9
- Вывести индексы и соответствующие им значения из массива.
Pascal
найти количество кратных чисел паскаль
var
a: array[2..9] of byte;
i,j: byte;
begin
for i:=2 to 9 do a[i] := 0;
for i:=2 to 99 do
for j:=2 to 9 do
if i mod j = 0 then
a[j] := a[j] + 1;
for i:=2 to 9 do
writeln(i,' - ', a[i]);
end
2 - 49
3 - 33
4 - 24
5 - 19
6 - 16
7 - 14
8 - 12
9 - 11
Язык Си
#include
main() {
int a[8], i, j;
for (i=0; i<9; i++) a[i] = 0;
for (i=2; i<100; i++)
for (j=2; j<10; j++)
if (i%j == 0) a[j-2] += 1;
for (i=0; i<8; i++)
printf("%d - %dn", i+2, a[i]);
}
Python
найти количество кратных чисел Python
a = [0]*8
for i in range(2,100):
for j in range(2,10):
if i%j == 0:
a[j-2] += 1
i = 0
while i < len(a):
print(i+2, ' - ', a[i])
i += 1
2 - 49
3 - 33
4 - 24
5 - 19
6 - 16
7 - 14
8 - 12
9 - 11
КуМир
алг кратность
нач
цел таб a[2:9]
цел j,i
нц для i от 2 до 9
a[i] := 0
кц
нц для j от 2 до 99
нц для i от 2 до 9
если mod(j,i) = 0 то a[i]:=a[i]+1 все
кц
кц
нц для i от 2 до 9
вывод i, " - ", a[i], нс
кц
кон
Basic-256
dim a(8)
for i=2 to 99
for j=2 to 9
if i%j = 0 then
a[j-2] = a[j-2] + 1
endif
next j
next ifor i=0 to 7
print (i+2) + " - " + a[i]
next i
Кратные числа, калькулятор
Кратное число – это число, делащееся на данное целое число без остатка; например 12 кратно 3.
Найти, вычислить кратные с калькулятором
Кратное – это произведение целого числа на любое другое целое число. Например, первые шесть чисел, кратных 3: 3, 6, 9, 12, 15 и 18. Это легко проверить на примерах ниже:
3 x 1 = 3 ;
3 x 2 = 6 ;
3 x 3 = 9 ;
3 x 4 = 12 ;
3 x 5 = 15 ;
3 x 6 = 18.
Два и более чисел могут иметь общие кратные. Например, наименьшее общее кратное (НОК) 3 и 7 равно 21, т. е. произведению этих двух чисел.
Наглядная таблица чисел кратных 3
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
- 50
– Кратные 3
У меня есть три числа x, y, z.
Для диапазона между числами x и y.
Как найти общие числа,% которых с z равно 0, то есть сколько чисел между x и y делятся на z?
Ответ 1
Это можно сделать в O (1): найти первую, найти последнюю, найти счетчик всех остальных.
Я предполагаю, что диапазон включен. Если ваши диапазоны являются эксклюзивными, настройте границы на единицу:
-
найдите первое значение после
x
, которое делится наz
. Вы можете отказаться отx
:x_mod = x % z; if(x_mod != 0) x += (z - x_mod);
-
найдите последнее значение до
y
, которое делится наy
. Вы можете отменитьy
:y -= y % z;
-
найдите размер этого диапазона:
if(x > y) return 0; else return (y - x) / z + 1;
Если доступны математические функции floor
и ceil
, первые две части могут быть написаны более читаемо. Также последнюю часть можно сжать с помощью математических функций:
x = ceil (x, z);
y = floor (y, z);
return max((y - x) / z + 1, 0);
если вход гарантированно является допустимым диапазоном (x >= y
), последний тест или max
не является обязательным:
x = ceil (x, z);
y = floor (y, z);
return (y - x) / z + 1;
Ответ 2
(2017, ответ переписан благодаря комментариям)
Число кратных z в числе n просто n / z
/
является целым делением, что означает десятичные знаки, которые могут возникнуть в результате деления, просто игнорируются (например, 17/5 => 3
, а не 3.4
).
Теперь, в диапазоне от x до y, сколько кратных z есть?
Посмотрим, сколько множителей m мы имеем до y
0----------------------------------x------------------------y
-m---m---m---m---m---m---m---m---m---m---m---m---m---m---m---
Вы видите, куда я иду… чтобы получить число кратных в диапазоне [ x, y ]
, получить число кратных y, а затем вычесть число кратных до x, (x-1) / z
Решение: ( y / z ) - (( x - 1 ) / z )
Программно, вы можете сделать функцию numberOfMultiples
function numberOfMultiples(n, z) {
return n / z;
}
чтобы получить число кратных значений в диапазоне [x, y]
numberOfMultiples(y) - numberOfMultiples(x-1)
Функция O (1), нет необходимости в цикле, чтобы получить число кратных.
Примеры результатов, которые вы должны найти
-
[30, 90] ÷ 13 => 4
-
[1, 1000] ÷ 6 => 166
-
[100, 1000000] ÷ 7 => 142843
-
[777, 777777777] ÷ 7 => 111111001
В первом примере 90 / 13 = 6
, (30-1) / 13 = 2
и 6-2 = 4
---26---39---52---65---78---91--
^ ^
30<---(4 multiples)-->90
Ответ 3
Я также столкнулся с этим на Codility. Мне потребовалось гораздо больше времени, чем мне хотелось бы признаться, чтобы придумать хорошее решение, поэтому я решил, что поделюсь тем, что я считаю элегантным решением!
Прямой подход 1/2:
O (N) временное решение с циклом и счетчиком, нереально, когда N = 2 млрд.
Удивительный подход 3:
Нам нужно количество цифр в некотором диапазоне, которые делятся на K.
Простой случай: предположим, диапазон [0.. n * K], N = n * K
N/K представляет количество цифр в [0, N), которые делятся на K, учитывая, что N% K = 0 (иначе, N делится на K)
ех. N = 9, K = 3, Num цифр = | {0 3 6} | = 3 = 9/3
Аналогичным образом,
N/K + 1 представляет количество цифр в [0, N], делимое на K
ех. N = 9, K = 3, Num цифр = | {0 3 6 9} | = 4 = 9/3 + 1
Я думаю, что понимание вышеизложенного факта – самая сложная часть этого вопроса, я не могу точно объяснить, почему он работает. Остальное сводится к сумме префиксов и обработке особых случаев.
Теперь у нас не всегда есть диапазон, который начинается с 0, и мы не можем предполагать, что две границы будут делиться на K. Но ждать! Мы можем исправить это, вычислив наши собственные хорошие верхние и нижние границы и используя некоторую магию вычитания 🙂
-
Сначала найдите самые близкие верх и низ в диапазоне [A, B], которые делятся на K.
- Верхняя граница (легче): напр. B = 10, K = 3, new_B = 9… шаблон B – B% K
- Нижняя граница: отл. A = 10, K = 3, new_A = 12… попробуйте еще немного, и вы увидите, что шаблон A – A% K + K
-
Затем рассчитайте следующее, используя вышеописанную технику:
- Определите общее количество цифр X между [0, B], которые делятся на K
- Определите общее количество цифр Y между [0, A), которые делятся на K
-
Рассчитайте количество цифр между [A, B], которые делятся на K в постоянное время по выражению X – Y
Веб-сайт: https://codility.com/demo/take-sample-test/count_div/
class CountDiv {
public int solution(int A, int B, int K) {
int firstDivisible = A%K == 0 ? A : A + (K - A%K);
int lastDivisible = B%K == 0 ? B : B - B%K; //B/K behaves this way by default.
return (lastDivisible - firstDivisible)/K + 1;
}
}
Я впервые объясняю такой подход. Обратная связь очень ценится 🙂
Ответ 4
Это один из вопросов урока Codility Lesson 3. По этому вопросу вход гарантированно находится в допустимом диапазоне. Я ответил на него с помощью Javascript:
function solution(x, y, z) {
var totalDivisibles = Math.floor(y / z),
excludeDivisibles = Math.floor((x - 1) / z),
divisiblesInArray = totalDivisibles - excludeDivisibles;
return divisiblesInArray;
}
https://codility.com/demo/results/demoQX3MJC-8AP/
(Я действительно хотел спросить о некоторых других комментариях на этой странице, но пока у меня недостаточно очков повторения).
Ответ 5
Разделите y-x
на z
, округляя вниз. Добавьте один, если y%z < x%z
или if x%z == 0
.
Нет математического доказательства, если кто-то не заботится о предоставлении одного, но тестовых примеров, в Perl:
#!perl
use strict;
use warnings;
use Test::More;
sub multiples_in_range {
my ($x, $y, $z) = @_;
return 0 if $x > $y;
my $ret = int( ($y - $x) / $z);
$ret++ if $y%$z < $x%$z or $x%$z == 0;
return $ret;
}
for my $z (2 .. 10) {
for my $x (0 .. 2*$z) {
for my $y (0 .. 4*$z) {
is multiples_in_range($x, $y, $z),
scalar(grep { $_ % $z == 0 } $x..$y),
"[$x..$y] mod $z";
}
}
}
done_testing;
Вывод:
$ prove divrange.pl
divrange.pl .. ok
All tests successful.
Files=1, Tests=3405, 0 wallclock secs ( 0.20 usr 0.02 sys + 0.26 cusr 0.01 csys = 0.49 CPU)
Result: PASS
Ответ 6
Вот мое короткое и простое решение на С++, которое получило 100/100 на кодовости.:)
Запуск в O (1) раз. Надеюсь, его не сложно понять.
int solution(int A, int B, int K) {
// write your code in C++11
int cnt=0;
if( A%K==0 or B%K==0)
cnt++;
if(A>=K)
cnt+= (B - A)/K;
else
cnt+=B/K;
return cnt;
}
Ответ 7
Пусть [A;B]
– интервал положительных целых чисел, включающий A и B, что 0 <= A <= B
, K – дивизор.
Нетрудно видеть, что в интервале [0;A]
существуют N(A) = ⌊A / K⌋ = floor(A / K)
факторы K:
1K 2K 3K 4K 5K
●········x········x··●·····x········x········x···>
0 A
Аналогично, существуют N(B) = ⌊B / K⌋ = floor(B / K)
факторы K в интервале [0;B]
:
1K 2K 3K 4K 5K
●········x········x········x········x···●····x···>
0 B
Тогда N = N(B) - N(A)
равно числу K (число целых чисел, делящихся на K) в диапазоне (A;B]
. Точка A не включена, так как вычитаемая N(A)
включает эту точку. Следовательно, результат должен быть увеличен на единицу, если A mod K
равен нулю:
N := N(B) - N(A)
if (A mod K = 0)
N := N + 1
Реализация в PHP
function solution($A, $B, $K) {
if ($K < 1)
return 0;
$c = floor($B / $K) - floor($A / $K);
if ($A % $K == 0)
$c++;
return (int)$c;
}
В PHP эффект функции floor
может быть достигнут путем нажатия на целочисленный тип:
$c = (int)($B / $K) - (int)($A / $K);
который, я думаю, быстрее.
Ответ 8
(floor)(high/d) - (floor)(low/d) - (high%d==0)
Объяснение:
Существуют числа a/d, делящиеся на d от 0.0 до a. (Д!= 0)
Следовательно, (пол) (высокий/д) – (пол) (низкий/д) даст числа, делящиеся в диапазоне (низкий, высокий) (обратите внимание, что низкий исключается, и высокий уровень включен в этот диапазон)
Теперь, чтобы удалить верхний из диапазона, просто вычтите (высокий% d == 0)
Работает для целых чисел, поплавков и т.д. (используйте функцию fmodf для поплавков)
Ответ 9
Не будет стремиться к решению o (1), это уйдет для более умного человека:) Просто чувствуйте, что это идеальный сценарий использования для программирования функций. Простой и понятный.
> x,y,z=1,1000,6
=> [1, 1000, 6]
> (x..y).select {|n| n%z==0}.size
=> 166
EDIT: после чтения другого решения O (1). Мне стыдно. Программирование заставило людей лениться думать…
Ответ 10
Разделение (a/b = c) по определению – взятие набора размеров a и формирование групп размера b. Число групп такого размера, которое может быть сформировано, c, является частным от a и b. – это не более чем число целых чисел в пределах диапазона/интервала] 0..a] (не считая нуля, но включая a), которые делятся на b.
поэтому по определению:
Y/Z – число целых чисел внутри] 0..Y], которые делятся на Z
и
X/Z – число целых чисел внутри] 0..X], которые делятся на Z
следующим образом:
result = [Y/Z] – [X/Z] + x (где x = 1 тогда и только тогда, когда X делится на Y в противном случае 0 – если данный диапазон [X..Y] включает X)
пример:
для (6, 12, 2) имеем 12/2 – 6/2 + 1 (как 6% 2 == 0) = 6 – 3 + 1 = 4//{6, 8, 10, 12}
для (5, 12, 2) имеем 12/2 – 5/2 + 0 (как 5% 2!= 0) = 6 – 2 + 0 = 4//{6, 8, 10, 12}
Ответ 11
Временная сложность решения будет линейной.
Фрагмент кода:
int countDiv(int a, int b, int m)
{
int mod = (min(a, b)%m==0);
int cnt = abs(floor(b/m) - floor(a/m)) + mod;
return cnt;
}
Ответ 12
здесь n подсчитает число и выведет сумму всех чисел, которые делятся на k
int a = sc.nextInt();
int b = sc.nextInt();
int k = sc.nextInt();
int first = 0;
if (a > k) {
first = a + a/k;
} else {
first = k;
}
int last = b - b%k;
if (first > last) {
System.out.println(0);
} else {
int n = (last - first)/k+1;
System.out.println(n * (first + last)/2);
}