Сделай мне минимальную магическую сумму


27

Удерживая эту задачу короткой.

Вам дают 4 числа: p1, p2, p3 и p4.

Магическая сумма чисел определяется следующим образом:

magic_sum = |p1 - p2| + |p2 - p3| + |p3 - p4| + |p4 - p1|

Вам разрешено изменять только одно из вышеуказанных целочисленных значений (p1, p2, p3 или p4). Вам нужно изменить значение так, чтобы магическая сумма значений достигла своего минимального значения.

Например:

p1, p2, p3, p4 = 17, -6, 15, 33. Значение магической суммы в этом случае равно 78.

Здесь вы можете изменить -6 на 16, и значение магической суммы станет 36, что является минимально достижимым значением.

Имейте в виду, что числа могут быть положительными или отрицательными целыми числами.

Это код-гольф, поэтому наименьшее количество байт в коде выигрывает. Брауни баллы за использование практического языка над языком отдыха. 4-го мая с вами.

Повторить:

Образец 1

Вход 1

17 -6 15 33

Выход 1

36

Объяснение 1

-6 можно заменить на 16, и это дает нам минимально возможную магическую сумму.

Образец 2

Вход 2

10 10 10 10

Выход 2

0 or 2

либо приемлемо

Объяснение 2

Минимальная достижимая магическая сумма равна 0, поскольку минимальная сумма из 4 натуральных чисел равна 0. Если число должно быть изменено, то одна из 10 может быть изменена на 9 и, таким образом, дает выход 2.

Образец 3

Вход 3

1 2 3 4

Выход 3

4

Объяснение 3

Ввод сам по себе дает 6 в качестве своей магической суммы. Изменение 4 на 1 и минимальная магическая сумма достигается 4.


10
+1, но мог бы сделать больше примеров.
Джонатан Аллан

2
Полностью проработанный пример и еще пара тестовых примеров, и это +1от меня.
Лохматый

@ Шэгги сделано. где мой +1? : P
Койшор Рой

1
@KoishoreRoy Разве тест-кейс 3 не будет 6 без изменений?
wizzwizz4

@ wizzwizz4 | 1 - 2 | + | 2 - 3 | + | 3 - 4 | + | 4 - 1 | = 1 + 1 + 1 + 3 = 6. Ты прав. Сделано редактирование.
Койшор Рой

Ответы:



20

Python 2 , 44 байта

a,b,c,d=sorted(input())
print min(c-a,d-b)*2

Попробуйте онлайн!

Сортирует входные данные a,b,c,d,в порядке возрастания, берет меньшее из c-aи d-bи удваивает его. Почему это работает?

Во-первых, обратите внимание, что когда мы меняем элемент, чтобы максимизировать до полной циклической суммы расстояний, оптимально (или привязано для оптимального) изменить его на равного соседу, например 17, -6, 15, 33 -> 17, 17, 15, 33. Это потому, что его новое общее расстояние до левого и правого циклических соседей - это, по крайней мере, расстояние между этими соседями, поэтому сделать их равными - это лучшее, что мы можем сделать.

Теперь удаление одной из двух смежных копий числа дает одинаковую циклическую сумму расстояний. В примере это 17, 15, 33, давая расстояния 2 + 18 + 16. Таким образом, вместо замены одного из четырех чисел эквивалентно просто удалить его, оставив три числа и используя сумму их циклических расстояний.

Обратите внимание, что с 3 числами наибольшее расстояние является суммой двух меньших. Это потому, что если мы отсортируем числа, чтобы иметь a ≤ b ≤ c, то |a - c| = |a - b| + |b - c|. Другими словами, мы путешествуем между самым большим и самым маленьким числом дважды, используя среднее число в качестве пит-стопа один раз. Таким образом, сумма трех расстояний просто вдвое больше расстояния между минимальным и максимальным, так что (c-a)*2.

Итак, вопрос в том, какое число мы удаляем, чтобы получить наименьшее расстояние между минимальным и максимальным из трех оставшихся чисел. Ясно, что мы удаляем наименьшее или наибольшее из чисел. Вызывая их a, b, c, dв отсортированном порядке, удаляя aлистья d - bи удаляя dлистья c - a, конечный результат будет двойным, в зависимости от того, что меньше.


помогите мне с тестовым случаем здесь. что если магическая сумма уже равна 0, что является наименьшим достижимым числом. в этом случае, ответ должен быть 0? или следующий наименьший возможный номер. Если входное значение равно [10,10,10,10], магическая сумма равна 0. Второе минимально возможное значение равно 2. Дайте мне знать, что вы думаете.
Койшор Рой

Я слышал от вас, что вы можете просто игнорировать порядок четырех указанных чисел (ваш первый шаг - отсортировать их). Но что , если бы мы попросили пять чисел p1через p5, и до сих пор разрешено только изменяя один номер? Случай с четырьмя числами кажется слишком простым (только после просмотра вашего ответа).
Джепп Стиг Нильсен

@KoishoreRoy Мне нравится ваше решение разрешить любой из них.
XNOR

@JeppeStigNielsen Да, тот факт, что порядок не имеет значения, является особенным для 4 чисел, и это происходит потому, что после удаления одного из трех чисел все пары чисел циклически соседствуют. С пятью числами это не сработает (вы наверняка найдете пример), и задача будет совсем другой.
XNOR

Хотелось бы, чтобы я проголосовал дважды. Прекрасное наблюдение, хорошо объяснено.
Иона

9

R , 66 33 байта

function(x)2*min(diff(sort(x),2))

Попробуйте онлайн!

Гораздо короче с алгоритмом xnor (прочитайте их объяснение и оставьте комментарий!).

Старая версия:

R , 66 байт

function(x,m=matrix(x,3,4))min(colSums(abs(diff(rbind(m,m[1,])))))

Попробуйте онлайн!

Принимает ввод как вектор из 4 целых чисел.

p2p2p1p2p3|p1p2|+|p2p3|p2=p1,

Есть 4 способа выбора номера, который мы меняем; для каждого из них нам нужно только вычислить сумму 3 абсолютных разностей.

3×4rbind


4

Желе , 11 10 байт

I;SASƲ$-ƤṂ

Попробуйте онлайн!

Монадическая ссылка, которая принимает список, если целые числа в качестве входных данных. Должен работать для произвольного размера списка. Работает на основе того, что минимальную сумму можно получить, протестировав удаление каждого числа из списка, вычисление магической суммы и взятие минимальной суммы.


3

Желе , 8 байт

ṁ-Ƥ⁸IA§Ṃ

Монадическая ссылка, принимающая список целых чисел *, которая дает целое число

* может быть любым числом, если их больше 1; используя магическую формулу того же стиля, суммируя различия между соседями.

Попробуйте онлайн!

Как?

ṁ-Ƥ⁸IA§Ṃ - Link: list of integers, X       e.g. [17,-6,15,33]
 -Ƥ      - for overlapping "outfixes" of length length(X)-1:
         -                                      [[-6,15,33],[17,15,33],[17,-6,33],[17,-6,15]]
ṁ  ⁸     -   mould like X                       [[-6,15,33,-6],[17,15,33,17],[17,-6,33,17],[17,-6,15,17]]
    I    - incremental differences              [[21,18,-39],[-2,18,-16],[-23,39,-16],[-23,21,2]]
     A   - absolute (vectorises)                [[21,18,39],[2,18,16],[23,39,16],[23,21,2]]
      §  - sums                                 [78,36,78,46]
       Ṃ - minimum                              36

3

Japt -Q , 11 байт

ñÍó ®r- ÑÃn

Использует алгоритм @ xnor, который сэкономил мне 4 байта.

Сохранено 5 байтов благодаря @Shaggy

Попытайся


кажется, работает нормально, но не могли бы вы объяснить, почему это работает?
Койшор Рой

@KoishoreRoy Добавлено объяснение
Воплощение неведения

29 байтдумаю )
лохматый

@ Шагая, когда я обновил свой ответ, я случайно заменил сумму на карту, что сделало некоторые гольфы недействительными, а другие хороши
Воплощение невежества

Приятно (далее) игра в гольф :) Вы можете сохранить еще 1 байт, заменив символ ÃÃновой строки.
Лохматый

3

J , 24 20 18 17 байт

альтернативная версия с использованием алгоритма xnor:

2*[:<./2 2-/@$\:~

как

Два раза 2 *мин 2 [:<./-й строки вычитается из первой строки [:-/матрицы 2x2, сформированной путем формирования 2 2$отсортированного ввода\:~

Попробуйте онлайн!

оригинальный ответ: J , 24 байта

[:<./1(1#.2|@-/\],{.)\.]

Попробуйте онлайн!

Используя идею Ника Кеннеди.

  • 1(...)\.] Примените глагол в скобках ко всем приставкам длины 1 (приставка длины n - это список с удаленными n смежными элементами, так что получается каждый возможный список с удаленным 1 вязом)
  • (1 #. 2 |@-/\ ] , {.)это вычисляет волшебную сумму, добавляя первый вяз к входным данным ] , {.и применяя разницу абс |@-/к инфиксам длины 2 2 ...\, и суммируя результат 1 #..
  • [:<./ возвращает мин

2

05AB1E , 11 7 байт

Порт @xnor 's Jelly ответа .
-4 байта благодаря @Emigna и @Grimy .

{2ô`αß·

Попробуйте онлайн.

7- байтовая альтернатива, которая работает только в устаревшей версии 05AB1E (потребует до ¥в новой версии):

{2ôø¥W·

Попробуйте онлайн.

Объяснение:

{        # Sort the (implicit) input-list
         #  i.e. [17,-6,15,33] → [-6,15,17,33]
 2ô      # Split this list into parts of size 2
         #  → [[-6,15],[17,33]]
   `     # Push both separated to the stack
    α    # And take their absolute differences
         #  → [23,18]
     ß   # Pop and push the minimum
         #  → 18
      ·  # Double it (and output implicitly as result)
         #  → 36

{        # Sort the (implicit) input-list
         #  i.e. [17,-6,15,33] → [-6,15,17,33]
 2ô      # Split this list into parts of size 2
         #  → [[-6,15],[17,33]]
   ø     # Zip/transpose, swapping rows/columns
         #  → [[-6,17],[15,33]]
    ¥    # Get the deltas/forward differences of the inner lists
         #  → [[23],[18]]
     W   # Get the flattened minimum (without popping)
         #  → 18
      ·  # Double it (and output implicitly as result)
         #  → 36

1
7 байтов в наследство: {2ôø¥W·или 8 с в перезаписи.
Эминья

2
7 байтов в не-наследии:{2ô`αW·
Grimmy

@ Emigna Smart, спасибо!
Кевин Круйссен

@ Grimy Спасибо также!
Кевин Круйссен

1

C ++ (gcc)

полная программа: 138 байт

#include<iostream>
#include<regex>
using namespace std;int main(){int a[4];for(int&b:a)cin>>b;sort(a,a+4);cout<<min(a[2]-*a,a[3]-a[1])*2;}

Попробуйте онлайн!

основная функция: 84 байта

#include<regex>
int m(int*a){std::sort(a,a+4);return std::min(a[2]-*a,a[3]-a[1])*2;}

Попробуйте онлайн!

Также используется алгоритм xnor, описанный в его посте Python 2.


0

Древесный уголь , 20 байтов

I⌊EEθΦθ⁻κμΣEι↔⁻λ§ι⊕μ

Попробуйте онлайн! Ссылка на подробную версию кода. Оказывается, я использую идею @ NickKennedy. Объяснение:

   Eθ                   Map over input array
     Φθ                 Filter over input array where
       ⁻κμ              Outer and inner indices differ
  E                     Map over resulting list of lists
           Eι           Map over remaining values in list
                §ι⊕μ    Get the next value in the list
             ↔⁻λ        Compute the absolute difference with the current value
          Σ             Take the sum of absolute differences
 ⌊                      Take the minimum sum
I                       Cast to string and implicitly print

0

JavaScript (ES6), 51 байт

Используя намного более умный метод xnor :

a=>([a,b,c,d]=a.sort((a,b)=>a-b),b+c<a+d?c-a:d-b)*2

Попробуйте онлайн!


Оригинальный ответ, 96 байт

Принимает ввод как массив из 4 целых чисел. Наверное, определенно не самый короткий подход.

a=>a.map(m=x=>a.map((y,i)=>a[m=a.map(v=>s+=Math.abs(p-(p=v)),a[i]=x,p=a[3],s=0)|m<s?m:s,i]=y))|m

Попробуйте онлайн!



0

Java 8 , 235 байт

Порт @Xnor's Python ответа и алгоритма

import java.util.*;interface M{static void main(String[]A){Scanner I=new Scanner(System.in);int a[]={0,0,0,0};for(int i=0;i<4;a[i++]=I.nextInt());java.util.Arrays.sort(a);System.out.print(2*(a[2]-a[0]>a[3]-a[1]?a[3]-a[1]:a[2]-a[0]));}}

Попробуйте онлайн!

Java 10 , бездоказательный, 222 байта

С Java 10 я смог бы заменить левую часть объявления Scanner var, хотя я не смог скомпилировать ее онлайн и, таким образом, я могу добавить ее только как пустяки. Сожалею.

interface M{static void main(String[]A){var I=new java.util.Scanner(System.in);int a[]={0,0,0,0};for(int i=3;i<4;a[i++]=I.nextInt());java.util.Arrays.sort(a);System.out.print(2*(a[2]-a[0]>a[3]-a[1]?a[3]-a[1]:a[2]-a[0]));}}

1
AFAIK, вы можете просто иметь функцию в качестве представления, например, как другие ответы сделали. Не нужно включать окружающий класс, интерфейс и т. Д.
Тау
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.