Fammi una somma magica minima


27

Mantenere questa sfida breve.

Ti vengono dati 4 numeri: p1, p2, p3 e p4.

La somma magica dei numeri è definita come segue:

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

È consentito modificare solo uno dei valori interi sopra indicati (p1, p2, p3 o p4). È necessario modificare il valore in modo tale che la somma magica dei valori raggiunga il suo valore minimo.

Per esempio:

p1, p2, p3, p4 = 17, -6, 15, 33. In questo caso il valore della somma magica è 78.

Puoi cambiare il -6 qui in 16, e il valore della somma magica diventerà 36, che è il valore minimo raggiungibile.

Tieni presente che i numeri possono essere numeri interi positivi o negativi.

Questo è code-golf, quindi vince meno byte nel codice. Brownie indica l'uso di una lingua pratica su una lingua ricreativa. Il 4 maggio sia con te.

Reiterare:

Campione 1

Ingresso 1

17 -6 15 33

Uscita 1

36

Spiegazione 1

Il -6 può essere sostituito con 16 e questo ci dà la somma magica minima raggiungibile possibile.

Campione 2

Ingresso 2

10 10 10 10

Uscita 2

0 or 2

o è accettabile

Spiegazione 2

La somma magica minima raggiungibile è 0 poiché la somma minima di 4 numeri interi positivi è 0. Se un numero deve essere modificato, uno dei 10 può essere cambiato in 9 e quindi produrre 2.

Esempio 3

Ingresso 3

1 2 3 4

Uscita 3

4

Spiegazione 3

L'input da solo produce 6 come somma magica. Cambiando il 4 in 1 e si ottiene la somma magica minima, che è 4.


10
+1, ma potrebbe fare con più esempi.
Jonathan Allan,

2
Un esempio pienamente funzionante e un altro paio di casi di test ed è un +1mio.
Shaggy

@Shaggy done. dov'è il mio +1? : P
Koishore Roy,

1
@KoishoreRoy Il test case 3 non sarebbe 6 senza la modifica?
wizzwizz4,

@ wizzwizz4 | 1 - 2 | + | 2 - 3 | + | 3 - 4 | + | 4 - 1 | = 1 + 1 + 1 + 3 = 6. Hai ragione. Fatto il montaggio.
Koishore Roy,

Risposte:


14

Gelatina , 6 byte

ṢŒœIṂḤ

Provalo online!

Una porta della mia risposta Python .

     (input)        [17, -6, 15, 33]
Ṣ    sort           [-6, 15, 17, 33]
Œœ   odd-even elts  [[-6, 17], [15, 33]]
I    increments     [23, 18]
M    minimum        18
Ḥ    double         36 

20

Python 2 , 44 byte

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

Provalo online!

Ordina l'input come a,b,c,d,in ordine crescente, prende il più piccolo di c-ae d-blo raddoppia. Perché funziona?

In primo luogo, nota che quando cambiamo un elemento per massimizzare la somma totale ciclica delle distanze, è ottimale (o legato per l'ottimale) cambiarlo per eguagliare un vicino, come 17, -6, 15, 33 -> 17, 17, 15, 33. Questo perché la sua nuova distanza totale dai suoi vicini ciclici sinistro e destro è almeno la distanza tra quei vicini, quindi rendere questi uguali è il meglio che possiamo fare.

Ora, l'eliminazione di una delle due copie adiacenti di un numero fornisce la stessa somma ciclica di distanze. Nell'esempio, questo è 17, 15, 33, dando distanze 2 + 18 + 16. Quindi, invece di sostituire uno dei quattro numeri, equivale a eliminarlo lasciando tre numeri e usando la somma delle loro distanze cicliche.

Si noti che con 3 numeri, la distanza più grande è la somma dei due numeri più piccoli. Questo perché se ordiniamo i numeri da avere a ≤ b ≤ c, allora |a - c| = |a - b| + |b - c|. In altre parole, viaggiamo due volte tra il numero più grande e quello più piccolo, usando una volta il numero medio come pit-stop. Quindi, la somma delle tre distanze è solo il doppio della distanza tra il minimo e il massimo, quindi (c-a)*2.

Quindi, la domanda è quale numero eliminiamo per ottenere la distanza minima tra il minimo e il massimo dei tre numeri che rimangono. Chiaramente eliminiamo il più piccolo o il più grande dei numeri. Chiamandoli a, b, c, din ordine ordinato, eliminando i afogli d - bed eliminando i dfogli c - a, e il risultato finale è il doppio di quello che è più piccolo.


aiutami con un caso di test qui. cosa succede se la somma magica è già 0, che è il numero più basso raggiungibile. in tal caso, la risposta dovrebbe essere 0? o il prossimo numero più basso possibile. Se l'input è [10,10,10,10], la somma magica è 0. il secondo più basso possibile è 2. Fammi sapere cosa ne pensi.
Koishore Roy,

Quello che ti sento dire è che puoi semplicemente ignorare l'ordine dei quattro numeri indicati (il tuo primo passo è quello di ordinarli). Ma cosa succede se avevamo chiesto cinque numeri p1attraverso p5, e ancora solo consentito cambiare un numero? Il caso a quattro numeri sembra troppo facile (solo dopo aver visto la tua risposta).
Jeppe Stig Nielsen

@KoishoreRoy Mi piace la tua soluzione di consentire uno dei due.
xnor

@JeppeStigNielsen Sì, il fatto che l'ordine non contenga è speciale per 4 numeri, e succede perché dopo averne eliminato uno per creare tre numeri, tutte le coppie di numeri sono ciclicamente adiacenti. Con cinque numeri questo non funzionerebbe (puoi sicuramente trovare un esempio) e la sfida sarebbe molto diversa.
xnor

Vorrei poter votare due volte. Bella osservazione, ben spiegata.
Giona

9

R , 66 33 byte

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

Provalo online!

Molto più breve con l'algoritmo di xnor (vai a leggere la loro spiegazione e vota il loro post!).

Vecchia versione:

R , 66 byte

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

Provalo online!

Accetta input come vettore di 4 numeri interi.

p2p2p1p2p3|p1-p2|+|p2-p3|p2=p1.

Ci sono 4 modi per scegliere quale numero cambiamo; per ognuno di questi, dobbiamo solo calcolare la somma di 3 differenze assolute.

3×4rbind


4

Gelatina , 11 10 byte

I;SASƲ$-ƤṂ

Provalo online!

Un collegamento monadico che accetta un elenco se numeri interi come input. Dovrebbe funzionare per dimensioni di elenco arbitrarie. Funziona sulla base del fatto che la somma minima può essere ottenuta testando la rimozione di ogni numero dall'elenco, calcolando la somma magica e prendendo il minimo.


3

Jelly , 8 byte

ṁ-Ƥ⁸IA§Ṃ

Un collegamento monadico che accetta un elenco di numeri interi * che produce un numero intero

* può essere un numero qualsiasi purché ce ne siano più di 1; usando la stessa formula magica di stile che riassume le differenze dei vicini che si avvolgono.

Provalo online!

Come?

ṁ-Ƥ⁸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 byte

ñÍó ®r- ÑÃn

Utilizza l'algoritmo di @ xnor, che mi ha salvato 4 byte.

5 byte salvati grazie a @Shaggy

Provalo


sembra funzionare bene, ma spiegheresti perché funziona?
Koishore Roy,

@KoishoreRoy Aggiunta una spiegazione
Incarnazione dell'ignoranza

29 byte ( penso )
Shaggy

@Shaggy quando ho aggiornato la mia risposta, ho accidentalmente sostituito la somma con la mappa, rendendo alcuni campi da golf non validi, ma altri sono buoni
Incarnazione dell'ignoranza

Ben (ulteriormente) golfed :) È possibile salvare 1 byte in più sostituendolo ÃÃcon una nuova riga.
Shaggy

3

J , 24 20 18 17 byte

versione alternativa usando l'algoritmo xnor:

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

Come

Due volte 2 *il minimo della [:<./seconda riga sottratto dalla prima riga [:-/della matrice 2x2 formata modellando 2 2$l'ingresso ordinato verso il basso\:~

Provalo online!

risposta originale: J , 24 byte

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

Provalo online!

Usando l'idea di Nick Kennedy.

  • 1(...)\.] applica il verbo tra parentesi a tutti gli outfix di lunghezza 1 (un outfix di lunghezza n è un elenco con n elementi contigui rimossi, quindi questo produce ogni possibile elenco con 1 olmo rimosso)
  • (1 #. 2 |@-/\ ] , {.)questo calcola la somma magica aggiungendo il primo olmo all'input ] , {.e applicando la differenza abs |@-/agli infissi di lunghezza 2 2 ...\e sommando il risultato 1 #..
  • [:<./ restituisce il min

2

05AB1E , 11 7 byte

Porto di @xnor risposta Jelly s' .
-4 byte grazie a @Emigna e @Grimy .

{2ô`αß·

Provalo online.

Alternativa a 7 byte che funziona solo nella versione legacy di 05AB1E (richiederebbe una versione precedente alla ¥nella nuova versione):

{2ôø¥W·

Provalo online.

Spiegazione:

{        # 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 byte in eredità: {2ôø¥W·o 8 con nella riscrittura.
Emigna

2
7 byte in non legacy:{2ô`αW·
Grimmy

@Emigna Smart, grazie!
Kevin Cruijssen,

@Grimy Grazie anche!
Kevin Cruijssen

1

C ++ (gcc)

programma completo: 138 byte

#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;}

Provalo online!

funzione principale: 84 byte

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

Provalo online!

Anche usando l'algoritmo xnor spiegato nel suo post su Python 2.


0

Carbone , 20 byte

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

Provalo online! Il collegamento è alla versione dettagliata del codice. Ho scoperto che sto usando l'idea di @ NickKennedy. Spiegazione:

   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

Java 8 , 235 byte

Una porta della risposta e dell'algoritmo Python di @ xnor

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]));}}

Provalo online!

Java 10 , non provato, 222 byte

Con Java 10, dovrei essere in grado di sostituire il lato sinistro della dichiarazione dello scanner con var, anche se non sono riuscito a compilarlo online e quindi posso solo aggiungerlo come curiosità. Scusate.

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 puoi solo avere una funzione come presentazione, come come hanno fatto le altre risposte. Non è necessario includere la classe circostante, l'interfaccia, ecc.
Tau
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.