An Array of Challenges # 3: Moving Medie


16

Nota: questo è il n. 3 in una serie di sfide di di . Per la sfida precedente, fai clic qui .

Media mobile di un elenco

La media mobile di un elenco è un calcolo che risulta in un nuovo elenco smussato, creato dalla media di piccoli elenchi sovrapposti dell'originale.

Quando creiamo una media mobile, per prima cosa generiamo l'elenco di liste secondarie sovrapposte utilizzando una certa "dimensione della finestra", spostando questa finestra a destra una volta ogni volta.

Ad esempio, dati l'elenco [8, 4, 6, 2, 2, 4]e le dimensioni della finestra 3, le liste secondarie sarebbero:

[8,  4,  6,  2,  2,  4]          Sublists:
(         )                  <-  [8, 4, 6]
    (         )              <-  [4, 6, 2]
        (         )          <-  [6, 2, 2]
            (         )      <-  [2, 2, 4]

Calcoliamo quindi la media media di ciascun elenco secondario per ottenere il risultato: [6.0, 4.0, 3.3, 2.7](ogni valore arrotondato al primo decimale).


La sfida

Il tuo compito è scrivere un programma o una funzione che, dato un elenco L e un numero intero 1 ≤ n ≤ lunghezza (L) , calcolino la media mobile per L usando la dimensione della finestra n .

Regole:

  • Il programma può utilizzare la divisione intera o la divisione float. Nel caso della divisione float, sono consentite piccole imprecisioni dovute alle limitazioni del tipo di dati, purché il valore sia altrimenti corretto.
  • Puoi inviare un programma completo o una funzione (ma non uno snippet).
  • Si può presumere che l'elenco conterrà solo numeri interi positivi .
  • Sono vietate le scappatoie standard.
  • Questo è , quindi vince la risposta più breve (in byte)!

Casi test

Si noti che, per facilità di leggibilità, tutti i valori sono arrotondati al primo decimale.

n=5, [1, 2, 3, 4, 5, 6, 7, 8]      ->      [3, 4, 5, 6]
n=3, [100, 502, 350, 223, 195]     ->      [317.3, 358.3, 256]
n=1, [10, 10, 10]                  ->      [10, 10, 10]
n=3, [10, 20, 30]                  ->      [20]
n=2, [90, 40, 45, 100, 101]        ->      [65, 42.5, 72.5, 100.5]

Dobbiamo arrotondare i valori float o possiamo lasciarli così come sono?
caird coinheringaahing il

3
@cairdcoinheringaahing Nota che, per facilità di leggibilità , tutti i valori sono arrotondati al primo decimale . Secondo me, puoi sicuramente lasciarli così come sono (almeno è quello che capisco).
Mr. Xcoder,

@cairdcoinheringaahing Sono stato abbastanza liberale con l'I / O: i valori interi o float vanno bene, puoi arrotondare se vuoi, ma non è necessario, e sono consentiti errori in virgola mobile
FlipTack

Va bene restituire frazioni anziché numeri in virgola mobile?
JungHwan Min,

@JungHwanMin Se per accuratezza, la tua lingua memorizzerà i valori come frazioni anziché float, è bene stamparli come frazioni accurate nelle loro forme più semplici.
FlipTack,

Risposte:




7

Haskell , 47 byte

n!a|length a<n=[]|_:t<-a=div(sum$take n a)n:n!t

Provalo online!

Due byte salvati grazie a xnor!


1
tail apuò essere estratto nella protezione.
xnor

Gah, sapevo che mi mancava qualcosa del genere. Grazie!
Lynn,

7

Dyalog APL, 4 byte

1 byte salvato grazie a @Graham

2 byte salvati grazie a @ jimmy23013

Ho già detto che APL non è una lingua da golf?

⊢+/÷

con na destra, o

+/÷⊣

con La destra.

Provalo online!

Come?

÷- dividi Lpern

⊢+/- ridurre +su windows din


Perché non dividere L per n prima della riduzione. Salva un byte
Graham,



@ jimmy23013 grazie mille! L'ho provato prima, ma devo aver sbagliato a scrivere gli argomenti perché non ha funzionato.
Uriel,

6

Python , 48 byte

f=lambda n,l:l[n-1:]and[sum(l[:n])/n]+f(n,l[1:])

Provalo online!

Una funzione ricorsiva. Più breve del programma (50 byte)

n,l=input()
while l[-n]:print sum(l[:n])/n;l=l[1:]

Provalo online!

Ciò consente di risparmiare 2 byte terminando con errore sulla whilecondizione.



4

Perl 6 , 33 byte

{@^a.rotor($^b=>1-$b)».sum X/$b}

Provalo

Allargato:

{  # bare block with placeholder parameters 「@a」, 「$b」

  @^a                # declare and use first param

  .rotor(            # split it into chunks
    $^b              # declare and use second param
    =>               # pair it with
    1 - $b           # one less than that, negated

  )».sum             # sum each of the sub lists

  X/                 # cross that using &infix:«/»

  $b                 # with the second param
}

4

C,  86   84  83 byte

i,j,s;f(a,l,n)int*a;{for(i=-1;i+++n<l;s=!printf("%d ",s/n))for(j=n;j--;)s+=a[i+j];}

Provalo online!

srotolato:

i, j, s;
f(a, l, n)int*a;
{
    for(i=-1; i+++n<l; s=!printf("%d ", s/n))
        for(j=n; j--;)
            s += a[i+j];
}

4

J, 7 5 byte

]+/\%

Provalo online!

Prende nl'argomento giusto e l'elenco come sinistra. Ringraziamo la soluzione di Uriel per l'idea di fare solo la sommatoria nell'infisso.

Spiegazione

]+/\%
    %  Divide list by n
]+/\   Sum on overlapping intervals of size n

Soluzione precedente (7 byte)

(+/%#)\
      \  Apply to overlapping intervals of size n
(+/%#)   Mean
 +/        Sum
   %       Divided by
    #      Length

4

Ohm v2 , 3 byte

ÇÆm

Provalo online!

Spiegazione:

ÇÆm  Main wire, arguments l (list) and n (integer)

Ç    All consecutive sublists of l with length n
 Æm  Arithmetic mean of each sublist

3

Pyth , 5 byte

.O.:F

Provalo qui!

Come funziona

.O.: F - Programma completo.

    F - Riduci l'input (elenco nidificato) con ...
  .: - ... Sublisti.
.O - Media di ciascuno.

3

Ottava , 33 31 byte

@(x,n)conv(x,~~(1:n)/n,'valid')

Provalo online!

Spiegazione

La convoluzione ( conv) è essenzialmente una somma ponderata mobile. Se i pesi vengono scelti come [1/n, ..., 1/n](ottenuti come ~~(1:n)/n) il risultato è una media mobile, di cui 'valid'viene conservata solo la parte.


2

R , 72 byte

function(l,n)(k=sapply(0:sum(l|1),function(x)mean(l[x+1:n])))[!is.na(k)]

Provalo online!

Calcola le finestre meandi tutte le dimensioni n; quando la finestra supera il bordo di l, i risultati sono NAquindi li filtriamo.

Pacchetto zoo R +, 13 byte

zoo::rollmean

Il zoopacchetto (infrastruttura S3 per serie temporali regolari e irregolari) ha molte funzioni utili. Puoi provarlo qui (violino a R) .


2

Japt v2.0a0, 7 byte

ãV ®x÷V

Provalo


Spiegazione

Input implicito di array U e numero intero V.

ãV

Ottieni sottosezioni di U lunghezzaV

®

Mappa sopra le sottosezioni.

÷V

Dividi ogni elemento per V .

x

Somma tutti gli elementi.




1

05AB1E , 5 byte

ŒsùÅA

Spiegazione:

Π    All substrings
 sù   Keep those only where the length is equal to <the second input>
   ÅA Arithmetic mean of each element in the resulting array.

Provalo online!



1

Proton , 46 byte

n=>l=>[sum(l[h to h+n])/n for h:0..len(l)-n+1]

Provalo online!

Si noti che ciò accetta input tramite la sintassi delle funzioni di curry e restituisce un elenco di frazioni.



0

Jq 1,5 , 61 byte

def f(N;L):[L|range(0;1+length-N)as$i|.[$i:$i+N]|add/length];

allargato

def f(N;L):
  [   L
    | range(0;1+length-N) as $i        # generate
    | .[$i:$i+N]                       # sublists
    | add/length                       # compute mean
  ];

Provalo online!


0

JavaScript (ES6), 53 byte

(l,n)=>l.map(e=>(s+=e-=a[i-n]||0)/n,s=i=0).slice(n-1)

0

PHP, 94 byte

function f($l,$n){while($i<=count($l)-$n)$r[]=array_sum(array_slice($l,$i++,$n))/$n;return$r;}

Provalo online!





0

K (oK) , 13 11 byte

Soluzione:

{+/+x':y%x}

Provalo online!

Esempi:

{+/+x':y%x}[3;8 4 6 2 2 4]
6 4 3.3333 2.6667
{+/+x':y%x}[5;1 2 3 4 5 6 7 8]
3 4 5 6

Spiegazione:

oK ha un built-in per la creazione di una finestra scorrevole, quindi riassumi le matrici risultanti e dividi per le dimensioni della finestra scorrevole per ottenere la media:

{+/+x':y%x} / the solution
{         } / lambda function taking x and y as implicit parameters
       y%x  / y (list) by x (sliding array size)
    x':     / sliding window of size x over list y
   +        / flip array (rotate by 90 degrees)
 +/         / sum up array

Sembra che non ti serva l'array di inversione +, e se K ha pendolarismo come APL puoi spostarti x%[commute]a sinistra e rilasciare le parentesi
Uriel

Il capovolgimento è necessario per garantire che la somma sia più ampia anziché in basso in ogni elenco e abbastanza sicura che non ci sia un operatore pendolare, almeno nulla che possa suggerirlo nel manuale . Saluti però!
streetster,

0

DataWeave , 50 byte

fun s(l,w)=0 to(sizeOf(l)-w)map avg(l[$ to $+w-1])
%dw 2.0
output application/json

fun sma(list: Array<Number>, window: Number) =
  0 to (sizeOf(list) - window)  // generate starting indices of sublists
  map list[$ to $ + window - 1] // generate sublists
  map avg($)                    // calculate averages

---
sma([90, 40, 45, 100, 101], 2)

0

Funky , 67 66 byte

Salvato un byte con sintassi del curry.

n=>t=>{k={}fori=0i<=(#t)-n i++k[i]=(forj=c=0c<n c++j+=t[i+c])/n k}

Provalo online!


0

Java 8, 111 byte

a->n->{int l=a.length-n+1,i=0,j;float[]r=new float[l];for(;i<l;r[i++]/=n)for(j=i;j<i+n;r[i]+=a[j++]);return r;}

Spiegazione:

Provalo qui.

a->n->{                 // Method with array and int parameters and float-array return-type
  int l=a.length-n+1,   //  New length of the return-array
      i=0,j;            //  Index-integers
  float[]r=new float[l];//  Return-array
  for(;i<l;             //  Loop (1) from 0 to `l` (exclusive)
      r[i++]/=n)        //    After every iteration, divide the current item by input `n`
    for(j=i;j<i+n;      //   Inner loop (2) from `i` to `i+n` (exclusive)
      r[i]+=a[j++]      //    Sum the result at index `i` with the items of the input-array
    );                  //   End of inner loop (2)
                        //  End of loop (1) (implicit / single-line body)
  return r;             //  Return the resulting float-array
}                       // End of method
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.