Знайдіть суму всіх чисел нижче n, кратних деякому набору чисел


31

Майже рівнозначно першому питанню Project Euler:

Якщо перерахувати всі натуральні числа нижче 10, кратні 3 або 5, отримаємо 3, 5, 6 і 9. Сума цих кратних дорівнює 23.

Знайдіть суму всіх кратних 3 або 5 нижче 1000.

Виклик:

З огляду на додатне ціле число Nта набір щонайменше одного натурального числа A, виведіть суму всіх додатних цілих чисел, менших за Nкратні, щонайменше, одного члена A.

Наприклад, для випадку Project Euler введенням буде:

1000
3
5

Тестові приклади:

Input : 50, [2]
Output: 600

Input : 10, [3, 5]
Output: 23

Input : 28, [4, 2]
Output: 182

Input : 19, [7, 5]
Output: 51

Input : 50, [2, 3, 5]
Output: 857

4
1) Чи вважаємо числа, кратні обом двічі? 2) Чи можемо ми отримати лише два інші числа? або будь-яка сума скаже один чи 3?
Пшеничний майстер

3
Чи можете ви навести кілька тестових випадків? Очевидно, не публікуйте відповіді на ПЕ, але що робити з іншими прикладами?
Rɪᴋᴇʀ

1
@WheatWizard: Слово "або" означає, що кожне число рахується лише один раз, максимум. Я погоджуюсь, що в питанні потрібно чітко визначити, скільки аргументів "числа, щоб перевірити кратність", повинні бути підтримані. Рівно два? Один чи більше? Нуль чи більше?
smls

1
Чи можемо ми взяти " числа, рівні або менші 10 ", або взяти 9 як введення замість 10?
Стюі Гріффін

"і набір принаймні одного натурального числа A", наскільки великим може бути набір?
betseg

Відповіді:


13

Желе , 6 байт

ḍþṖḅTS

Спробуйте в Інтернеті!

Як це працює

ḍþṖḅTS  Main link. Left argument: D (array). Right argument: n (integer)

ḍþ       Divisible table; test each k in [1, ..., n] for divisibility by all
        integers d in D.
  Ṗ     Pop; discard the last Boolean array, which corresponds to n.
   ḅ    Unbase; convert the Boolean arrays of base n to integer. This yields a 
        non-zero value (truthy) and and only if the corresponding integer k is 
        divisible by at least one d in D.
    T   Truth; yield the array of all indices of truthy elements.
     S  Compute their sum.

3
Звичайно, @Dennis повинен придумати щось, що змусить вас замислитись, що ви робите на ppcg
Grajdeanu Alex.

8

Пітон, 59 55 байт

lambda n,l:sum(v*any(v%m<1for m in l)for v in range(n))

repl.it

Безіменна функція, що приймає ціле число, nі список цілих чисел l. Проходить діапазон натуральних чисел (плюс нуль) до, але не включаючи, nі сум ( sum(...)) тих, що мають залишок після ділення нуля ( v%m<1) для anyцілих чисел mу списку l. Для збереження 3 байтів використовується множення, а не умовне.


8

Октава, 38 36 33 байт

@(x,y)(1:--x)*~all(mod(1:x,y),1)'

Візьміть вхід як: f(10, [3;5]). Це було б на 2 байти коротше, якби введення могло бути f(9,[3;5])для одного тестового випадку.

Перевірте всі тестові випадки тут.


Пояснення:

@(x,y)        % Anonymous function that takes two inputs, x and y
              % x is a scalar and y is a vertical vector with the set of numbers
(1:--x)*      % Pre-decrement x and create a vector 1 2 ... x-1    

Octave може попередньо зменшити розмір, тому використання 1:--xзамість 1:x-1(два рази) зберігає два байти.

mod(a,b)дає 1 2 0 1 2 0 1 2 0за mod(1:9,3). Якщо другий аргумент є вертикальним вектором, він буде повторювати перший вхід по вертикалі і прийме модуль для кожного зі значень другого вхідного аргументу. Отже, для введення mod(1:9, [3;5])це дає:

1 2 0 1 2 0 1 2 0
1 2 3 4 0 1 2 3 4

Зважаючи ~all(_,1)на це, trueдля стовпців, де принаймні одне значення дорівнює нулю, і falseде всі значення не нульові:

~all(mod(1:x,y),1)
0 0 1 0 1 1 0 0 1

,1Потрібно в разі , якщо є тільки один номер в y. Інакше він діятиме на весь вектор замість числа за номером.

Транспонуючи це у вертикальну матрицю та використовуючи множення матриці, дасть нам правильну відповідь, не потребуючи явного підсумовування:


О, це жорстоко: мені довелося додати 2 байти через різницю між x і x – 1, але ти повинен був додати 4 байти, і я зараз попереду на 1 байт> :)
Грег Мартін

6

JavaScript (ES6), 40 39 36 байт

Введення: ціле число nта масив цілих чисел aіз синтаксисом currying(n)(a)

n=>F=a=>n--&&!a.every(v=>n%v)*n+F(a)

Тестові справи


У мене був трохи інший склад для однієї і тієї ж довжини: f=(n,a)=>n--&&a.some(v=>n%v<1)*n+f(n,a). Найкраще, що я міг зробити безрекурсивно, було 61 байт.
Ніл

@Neil Ваш коментар спонукав мене шукати ще одну формулювання. Цікаво, що синтаксис currying економить 3 байти.
Арнольд

5

1
Просто перевіряю, чи читаю я це право (без перевірки документів). Ти декрементуєш, створюєш вектор 1 2 .... Ви дублюєте його і приймаєте за модулем інший вхід. Ви заперечуєте його і множите з вектором 1 2 .., використовуйте унікальні для позбавлення від дублікатів і, нарешті, підсумовуючи його ...
Стюі Гріффін

Саме так! Я на мобільному, тому я не включав пояснення. Зараз це не обов’язково :-)
Луїс Мендо


4

Пітон, 67 байт

a,b,c=input()
x=y=0
exec("if x%c<1or 1>x%b:y+=x\nx+=1\n"*a)
print y

Написавши це, я помітив, що мій код був схожий на існуючу відповідь python, проте я придумав його самостійно, і все одно публікую його.


Точка з комою не потрібна у виконанні, оскільки у вас все одно є розрив рядка. Я знав, що моя відповідь може бути перевершена!
Тео

Специфікація говорить "набір принаймні одного натурального числа"; це, здається, обробляє лише той випадок, коли множина є двома цілими числами. Також наявність x=y=0окремого рядка дозволить зберегти чотири байти.
Джонатан Аллан

@JonathanAllan здорово, велике спасибі!
Rɪᴋᴇʀ

4

Математика, 37 27 байт

Дякую Мартіну Ендеру за ретельне спостереження, яке призвело до великих байтових заощаджень!

Tr[Union@@Range[#,#2-1,#]]&

Безіменна функція, що приймає два аргументи, список #цілих чисел (потрібні дільники A) та ціле число #2(верхня межа N) та повертає ціле число. Range[#,#2-1,#]дає для кожного елемента dсписку #всі кратні dменші або рівні #-1(отже, менше #); Об'єднання цих списків потім обчислюється та підсумовується Tr.

Попередня версія:

Tr[x=#;Union@@(Range[#,x-1,#]&/@#2)]&

1
Rangeє в списку: Tr[Union@@Range[#2,#-1,#2]]&(а потім збережіть інший байт, змінивши порядок входів)
Мартін Ендер

4

Perl 6 , 25 байт

{sum grep *%%@_.any,^$^a}

Лямбда, яка приймає вхідні числа як аргументи. (Один аргумент для N та довільна кількість аргументів для A).

( Спробуйте в Інтернеті. )

Пояснення:

  • { ... }: Лямбда.
  • $^a: Перший аргумент лямбда.
  • @_: Залишилися аргументи лямбда ("варіаційний параметр").
  • ^$^a: Діапазон від 0до $^a - 1.
  • * %% @_.any: Ще одна лямбда, яка тестує свій аргумент, *використовуючи оператор, що ділиться, %%проти - any- З'єднання списку @_.
  • grep PREDICATE, RANGE: ітератує діапазон чисел і повертає ті, для яких присудок є істинним.

Я думаю, що додавання ^для оголошення параметра заповнювача досить явне. Тим більше, що ви могли використовувати його пізніше в блоці як просто $a. Я думаю, що тільки $_ @_ %_ selfколи-небудь можна вважати неявно заявленим. Я думаю, що я хотів би прочитати цей рядок " оголосити перший параметр як заповнювач "
Бред Гілберт b2gills

@ BradGilbertb2gills: Я мав на увазі, що це неявно стає частиною підпису лямбда, хоча код не вводив підпис перед тілом лямбда. @_і, що %_стосується функцій, в цьому відношенні не відрізняються: вони теж стають частиною підпису, лише якщо вони з’являються в тілі. Тільки $_selfі %_в методах) може стати частиною підпису за замовчуванням.
smls

PS: Зараз я видалив фразу "неявно оголошено", оскільки це не потрібно для розуміння коду.
smls

3

R, 67 байт

a=scan();x=c();for(i in a[-1])x=c(x,seq(i,a[1]-1,i));sum(unique(x))

Приймає вектор до STDIN в наступному форматі: [N, a_1, a_2, ...]. Підтримує будь-яку кількість a. Для кожного a, створює послідовність , aщоб N-1з розмір кроку a. Потім береться сума всіх унікальних записів у цьому векторі.


3

Haskell, 42 39 байт

a!b=sum[x|x<-[1..a-1],any((<1).mod x)b]

Використання:

Main> 50![2,3,5]
857

Завдяки @Zgarb за 3 байти


(x`mod`)те саме, що mod x.
Згарб

@Zgarb whoops :)
Angs

3

05AB1E , 9 байт

FND²%P_*O

Спробуйте в Інтернеті!

F         For N in [0, ..., input[0]-1]
 ND²%     Evaluate N%input[1]; yields an array of results
     P    Take the total product of the array. Yields 0 only if at least one of the value is 0, in other words if N is multiple of at least one of the specified values
      _   Boolean negation, yields 1 if the last value is 0 and yields 0 otherwise
       *  Multiply by N: yields N if the last value is 0 and yields 0 otherwise
        O Display the total sum

8 байт або 8 байт альтернативно за допомогою фільтра . (Перший 8-байтний не вдався, коли ви опублікували свою відповідь. Оскільки à(максимум) з'являється цей список зараз, але не раніше.)
Кевін Круїйсен

3

Октава, 49 37 байт

@(A,N)sum(unique((z=(1:N)'.*A)(z<N)))

функція буде називатися як f([2 3 4],50)

Припустимо, що A=[2 3 4];нам потрібно мати суму чисел як

sum(
2,4,6...,50-1 ,
3,6,9...,50-1,
4,8,12,...50-1)

ми можемо помножити [2 3 4]на , 1:50щоб отримати матрицю(1:N)'.*A

[2 4 6 ... 2*50
3 6 9 ... 3*50
4 8 12 ...4*50]

потім дістаньте з матриці ті, які менші за 50: z(z<N)

Оскільки в матриці є повторювані елементи, ми дістаємо унікальні значення та підсумовуємо їх.

попередня відповідь : (це рішення не вдасться, якщо N == 1)

@(A,N)sum((k=uint64(1:N-1))(any(k==(k./A').*A')))

функцію слід називати як f(unit64([2 3 4]),uint64(50))


1
Дуже хороша! Майже настільки ж наче відповідь на іншу октаву, але зовсім інший підхід. Це мені зовсім не спадало на думку! Можливо, ви можете отримати певне пояснення і, можливо, посилання на ideone, але ви вже маєте свій голос :-)
Стюі Гріффін

Я змінив порядок введення, але ось посилання ideone.com/8Bljrl
Гріффін

2

Pyth, 10 байт

s{sm:0hQdt

Пояснення

s{sm:0hQdtQ   Implicit input
    :0hQd     Get multiples of d below the bound
   m     tQ   ... for each d given
  s           Concatenate results
 {            Remove repeats
s             Take the sum

2

T-SQL, 87 байт

Це працюватиме до тих пір, поки @iмає значення 2048 або нижче

USE master--needed for databases not using master as default
DECLARE @i INT=50
DECLARE @ table(a int)
INSERT @ values(2),(3),(5)

SELECT sum(distinct number)FROM spt_values,@ WHERE number%a=0and abs(number)<@i

Спробуй


2

APL (Dyalog Unicode) , 12 байт

+/⊢∘⍳∩∘∊×∘⍳¨

Спробуйте в Інтернеті!

Анонімна негласна функція. Завдяки @ Adám за те, що він допомагав мені відголити 3 байти від цього. Використання ⎕IO←0.

Як:

+/⊢∘⍳∩∘∊×∘⍳¨  Tacit function. Left and right arguments will be called  and  respectively.

        ×∘⍳¨  Multiply  with each element of [0..⍵-1]
             Enlist (flattens the vector)
     ∩∘       Then, get the intersection of that vector with
  ⊢∘⍳         The vector [0..⍵-1].
+/            Then sum

2

Піп , 43 41 39 35 байт

b^:sFc,a{f:0Fdb{f?0c%d?0(f:i+:c)}}i

Спробуйте в Інтернеті!

Пояснення:

Takes inputs like so:

    arg1 1000
    arg2 3 5

b^:s                      ;read rest of inputs as array
                          ;(s is " " and ^ is split into array on char)
F c ,a{                   ;for(c in range(0,a))
  f:0                     ;flag to prevent double counting 15,30,etc.
  F d b {                 ;forEach(d in b)
    f? 0 c%d? 0 (f:i+:c)  ;if flag {continue}elif c%d {f=i+=c}
                          ;      (i will always be truthy so why not)     
  }
}
i                         ;print sum

ой! Я читаю занадто швидко
Кеннет Тейлор

Набагато краще. Чудова відповідь!
mbomb007

1

Пітон 2, 80 байт

Це дуже довго. Однозначно можна скоротити. Якщо взяти 3 числа як окремі введення, це, безумовно, шкодить оцінці.

i=input
x=i();y=i();z=i();s=c=0
exec("if c%z<1 or c%y<1:s+=c\nc+=1\n"*x)
print s

Ви можете зробити x,y,z=input()та дати внесок у вигляді (1000,3,5).
Skyler

1

Common Lisp, 77

(lambda(n x)(loop for i below n when(some(lambda(u)(zerop(mod i u)))x)sum i))

Безумовно

(lambda (limit seeds)
  (loop for i below limit
        when (some (lambda (u) (zerop (mod i u))) seeds)
          sum i))

1

PowerShell , 57 байт

param($a,$b)(1..--$a|?{$i=$_;$b|?{!($i%$_)}})-join'+'|iex

Спробуйте в Інтернеті!

Ітеративне рішення. Приймає введення як число $aі як буквальний масив $b. Цикли від 1до одного нижче $a(через --$a), використовуючи Where-Objectоператор |?{...}з пропозицією для вибору певних чисел.

Цей пункт встановлює $iпоточне число перед тим, як надсилати вхідний масив $bв інший |?{...}, тут вибираються ті елементи, де поточне число рівномірно ділиться принаймні на одне з чисел у $b. Ті елементи $b, які поділяються рівномірно, залишаються на трубопроводі.

Таким чином, якщо є щонайменше один елемент з $b, трубопровід містить елемент, тому зовнішній Whereє $trueі поточне число залишається на трубопроводі. В іншому випадку, без елементів $bна трубопроводі, зовнішній Whereє $false, тому поточне число не розміщується на трубопроводі.

Ці числа зібрані в паренах, -joinзібрані разом із +знаками, і покладені на них |iex(скорочено Invoke-Expressionі схоже на eval). Результат підсумовування залишається на конвеєрі, а вихід неявний.


1

PHP, 78 76 74 байт

for(;++$i<$argv[$f=$k=1];$s+=$i*!$f)for(;$v=$argv[++$k];)$f*=$i%$v;echo$s;

Зовнішній цикл проходить $iвід 1 до рівня нижче першого аргументу і додає $iдо , $sякщо $fце НЕ встановлено.
У примножує внутрішній цикл $fз ( по $iмодулю аргументу) для всіх наступних аргументів, вважаючи , $fщоб , 0якщо $iце кратно будь-який з них.

Бігайте з -r.


1

Скала, 47 байт

n=>1.to(n(0)-1).filter(i=>n.exists(i%_==0)).sum

n - Список, який містить перший аргумент N, решта - елементиA

Працює шляхом фільтрації чисел, де не існує принаймні одного A, з яких i є кратним, а потім підсумовування. Власне кажучи, ми повинні використовувати n.tail.existsвсередині замикання, але оскільки я завжди менший за N, і тому ніколи не кратний N, рішення все-таки є повним без цього.



1

Рубі, 52 48 46 байт

->b{b[s=0].times{|x|b.find{|y|x%y<1&&s+=x}};s}

1

C11, 177 байт

#include"object.h"
#define S size_t
S g(S m,array_t*d){S s,i,l,j;for(s=i=0;i<m;i++){for(l=1,j=0;j<d->idx+1;l*=i%(S)(*array_get_ref(d,j++,NULL))->fwi->value);s+=l?0:i;}return s;}

Потрібен цей набір заголовків у тій же папці таfnv-hash бібліотека, яка там також знайдена. Компілюй якgcc 1.c ../fnv-hash/libfnv.a -o 1 -DNODEBUG

Тестова програма:

#include "../calc/object/object.h"
#include <stdio.h>

size_t f (const size_t max, const size_t a, const size_t b);
size_t f2 (const size_t max, const array_t* const divs);
size_t g (size_t max, array_t* divs);

define_array_new_fromctype(size_t);

int main(void) {
  printf("%zu\n", f(10, 3, 5));
  static const size_t a[] = {
    3, 5
  };
  array_t* b = array_new_from_size_t_lit(a, 2, t_realuint);
  printf("%zu\n", f2(10, b));
  printf("%zu\n", g(10, b));
  array_destruct(b);
  return 0;
}

size_t f (const size_t max, const size_t a, const size_t b) {
  size_t sum = 0;
  for (size_t i = 0; i < max; i++) {
    sum += (i % a * i % b) ? 0 : i;
  }
  return sum;
}

size_t f2 (const size_t max, const array_t* const divs) {
  size_t sum = 0;
  const size_t len = array_length(divs);

  for (size_t i = 0; i < max; i++) {
    size_t mul = 1;
    for (size_t j = 0; j < len; j++) {
      object_t** this = array_get_ref(divs, j, NULL);

      fixwid_t*   num = (*this)->fwi;

      mul *= i % (size_t) num->value;
    }
    sum += mul ? 0 : i;
  }
  return sum;
}

#define S size_t
S g(S m,array_t*d){S s,i,l,j;for(s=i=0;i<m;i++){for(l=1,j=0;j<d->idx+1;l*=i%(S)(*array_get_ref(d,j++,NULL))->fwi->value);s+=l?0:i;}return s;}

виходи

23
23
23

1

Japt -x, 9 7 6 байт

Ç*VøZâ

Спробуй це

           :Implicit input of integer U and array V
Ç          :Map each Z in the range [0,U)
 *         :  Multiply by
  Vø       :  Does V contain
    Zâ     :   Any of the divisors of Z
           :Implicit output of sum of resulting array

1

Шепіт v2 , 178 байт

> Input
> Input
> ℕ
>> (1)
>> ∤L
>> {L}
>> L∩2
>> #L
>> L∈3
>> L⋅R
>> Each 5 4
>> Each 6 11
>> Each 7 12
>> Each 8 13
>> Each 9 14
>> Each 10 15 4
>> ∑16
>> Output 17

Спробуйте в Інтернеті!

Дерево структури:

дерево дерево

Як це працює

EachLα

f(х)={i|(i|х),iN}тобто сукупність дільниківхг(х)=f(х)αтобто об'єднання дільників Росіїхзαгод(х)=|г(х)|>0тобтог(х)не порожній

Це те, що представляють рядки від 5 до 10 . Рядки 11αβ

βi={αiгод(αi)0год(αi)

αiiαββ0


1

K (oK) , 15 14 байт

Рішення:

{+/&|/~y!\:!x}

Спробуйте в Інтернеті!

Приклади:

{+/&|/~y!\:!x}[50;,2]
600
{+/&|/~y!\:!x}[10;3 5]
23

Пояснення:

{+/&|/~y!\:!x} / the solution
{            } / lambda taking implicit x and y
           !x  / range 0..x-1
       y!\:    / modulo (!) x with each-left (\:) item in y
      ~        / not
    |/         / min-over to flatten into single list
   &           / indices where true
 +/            / sum up


0

Обробка, 88 байт

int q(int a,int[]b){int s=0,i=0;for(;++i<a;)for(int j:b)if(i%j<1){s+=i;break;}return s;}

Використовує простий forпідхід-петля, підсумовує всі кратні вгору і повертає його. Вхід - це формат int, int[]масив.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.