Trouvez la sous-matrice avec la plus petite moyenne

21

On vous donne une matrice n-par-m d'entiers, où n, m> 3 . Votre tâche consiste à trouver la sous-matrice 3 x 3 qui a la moyenne la plus faible et à sortir cette valeur.

Règles et clarifications:

  • Les entiers seront non négatifs
  • Format d'entrée et de sortie en option
  • La sortie doit être précise jusqu'à au moins 2 décimales (si elle n'est pas entière)
  • Les sous-matrices doivent être constituées de lignes et de colonnes consécutives

Cas de test:

35    1    6   26   19   24
 3   32    7   21   23   25
31    9    2   22   27   20
 8   28   33   17   10   15
30    5   34   12   14   16
 4   36   29   13   18   11 

Minimum mean: 14

100    65     2    93
  3    11    31    89
 93    15    95    65
 77    96    72    34

Minimum mean: 46.111

1   1   1   1   1   1   1   1
1   1   1   1   1   1   1   1
1   1   1   1   1   1   1   1
1   1   1   1   1   1   1   1

Minimum mean: 1

4   0   0   5   4
4   5   8   4   1
1   4   9   3   1
0   0   1   3   9
0   3   2   4   8
4   9   5   9   6
1   8   7   2   7
2   1   3   7   9

Minimum mean: 2.2222

Il s'agit de donc le code le plus court dans chaque langue l'emporte. J'encourage les gens à poster des réponses dans les langues déjà utilisées, même si elles ne sont pas plus courtes que la première.

Stewie Griffin
la source
Il serait également intéressant d'avoir un défi avec des lignes et des colonnes pas nécessairement contiguës
Luis Mendo
Non, allez-y vous-même :-)
Luis Mendo
Voulez-vous dire des entiers au sens mathématique ou du type de données, c'est-à-dire, pouvons-nous prendre une matrice de flottants intégraux?
Dennis
Sens mathématique. Est-ce une chose que j'ai apprise ici, c'est que vous pouvez faire des hypothèses sur les types de données dans différentes langues ...
Stewie Griffin
Doux, cela économise un octet. Merci de clarifier.
Dennis

Réponses:

11

Gelée , 11 9 octets

+3\⁺€F÷9Ṃ

Enregistré 2 octets grâce à @ Dennis .

Essayez-le en ligne!

Explication

+3\⁺€F÷9Ṃ  Main link. Input: 2d matrix
+3\        Reduce overlapping sublists of size 3 by addition
   ⁺€      Repeat previous except over each row
     F     Flatten
      ÷9   Divide by 9
        Ṃ  Minimum
miles
la source
1
Oh,> _ <bien sûr: D
Jonathan Allan
Je serais intéressé par une version non golfée de la gelée, car elle a tellement de fonctions utiles.
J Atkin
1
+3\⁺€F÷9Ṃenregistre quelques octets.
Dennis
@ Dennis Wow, est-ce vraiment le traitement en +3\premier et le doublon +3\€? Je ne m'attendais pas à ce que cela se produise
miles
1
L'analyseur est essentiellement basé sur la pile; \pops 3et +et pousse le quicklink +3\, pops le la quicklink et pousse deux copies, puis apparaît la copie et supérieure pousse une version de cartographie.
Dennis
8

Octave, 38 octets

@(M)min(conv2(M,ones(3)/9,'valid')(:))
Rainer P.
la source
8

MATL , 13 9 octets

3thYCYmX<

Port de la réponse de @ rahnema1 .

Essayez-le en ligne!

Comment ça marche

Tenez compte des commentaires

[100 65  2 93;
   3 11 31 89;
  93 15 95 65;
  77 96 72 34]

par exemple.

3th   % Push [3 3]
      % STACK: [3 3]
YC    % Input matrix implicitly. Convert 3x3 sliding blocks into columns
      % STACK: [100   3  65  11;
                  3  93  11  15;
                 93  77  15  96;
                 65  11   2  31;
                 11  15  31  95;
                 15  96  95  72;
                  2  31  93  89;
                 31  95  89  65;
                 95  72  65  34]
Ym    % Mean of each column
      % STACK: [46.1111 54.7778 51.7778 56.4444]
X<    % Minimum of vector. Display implicitly
      % STACK: [46.1111]
Luis Mendo
la source
7

Mathematica, 37 35 octets

Merci @MartinEnder pour 2 octets!

Min@BlockMap[Mean@*Mean,#,{3,3},1]&

Explication

Min@BlockMap[Mean@*Mean,#,{3,3},1]&
    BlockMap[                    ]&  (* BlockMap function *)
                        #            (* Divide the input *)
                          {3,3}      (* Into 3x3 matrices *)
                                1    (* With offset 1 *)
             Mean@*Mean              (* And apply the Mean function twice to
                                        each submatrix *)
Min                                  (* Find the minimum value *)
JungHwan Min
la source
Très très lisse!
Greg Martin
5

Python 2 , 93 81 80 79 octets

f=lambda M:M[2:]and min(sum(sum(zip(*M[:3])[:3],()))/9,f(M[1:]),f(zip(*M)[1:]))

Essayez-le en ligne!

Comment ça marche

f est une fonction récursive qui prend une liste de tuples (ou tout autre itérable 2D indexable qui représente une matrice M ) et calcule récursivement le minimum de la moyenne de la sous-matrice 3 × 3 dans le coin supérieur gauche et f est appliqué récursivement à M sans sa première ligne et M sans sa première colonne.

f(M) fait ce qui suit.

  • Si M a moins de trois lignes, M[2:]est une liste vide, que f renvoie.

    Notez que, puisque n> 3 lors de la première exécution, l'initiale ne peut pas renvoyer une liste vide.

  • Si M a trois lignes ou plus, M[2:]n'est pas vide et donc véridique, donc le code à droite de andest exécuté, renvoyant le minimum des trois valeurs suivantes.

    min(sum(sum(zip(*M[:3])[:3],()))/9

    M[:3]donne les trois premières lignes de M , zip(*...)transpose les lignes et les colonnes (donnant une liste de tuples), sum(...,())concatène tous les tuples (cela fonctionne parce que +c'est la concaténation) et sum(...)/9calcule la moyenne de la liste résultante de neuf entiers.

    f(M[1:])

    applique récursivement f à M avec sa première ligne supprimée.

    f(zip(*M)[1:])

    transpose les lignes et les colonnes, supprime la première ligne du résultat (donc la première colonne de M , et applique récursivement f au résultat.

Notez que la couche précédemment supprimée dans un appel récursif sera toujours une ligne, donc tester si M a suffisamment de lignes sera toujours suffisant.

Enfin, on peut s'attendre à ce que certains appels récursifs renvoyés []soient un problème. Cependant, en Python 2 , chaque fois que n est un nombre et A est un itérable, la comparaison n < Arenvoie Vrai , donc le calcul du minimum d'un ou plusieurs nombres et un ou plusieurs itérables retournera toujours le nombre le plus bas.

Dennis
la source
3

J , 21 octets

[:<./@,9%~3+/\3+/\"1]

Essayez-le en ligne!

La bonne façon d'opérer sur les sous-tableaux en J est d'utiliser la troisième _3forme de coupure ( ) ;.x (u;._3) ysignifie appliquer le verbe usur chaque sous x-tableau complet de la taille du tableau y. Une solution utilisant cela ne nécessite qu'un octet de plus, mais sera beaucoup plus efficace sur les baies plus grandes.

[:<./@,9%~3 3+/@,;._3]

Essayez-le en ligne!

Explication

[:<./@,9%~3+/\3+/\"1]  Input: 2d array M
                    ]  Identity. Get M
                  "1   For each row
              3  \       For each overlapping sublist of size 3
               +/          Reduce by addition
          3  \         For each overlapping 2d array of height 3
           +/            Reduce by addition
       9%~             Divide by 9
[:    ,                Flatten it
  <./@                 Reduce by minimum
miles
la source
1
J'aime la façon dont []ils ressemblent, mais ce n'est vraiment pas le cas.
Lynn
1
@Lynn Attendez une seconde, ce n'est pas vrai. J est censé distraire les téléspectateurs avec plusieurs supports asymétriques. Aurait dû utiliser un [ou |:)
miles
2

Gelée , 18 octets

Vous avez raté l'astuce, telle qu'utilisée par miles dans leur réponse , d'utiliser une réduction cumulative n-sage de l'addition - toute la première ligne peut être remplacée par +3\pour 11.

ẆµL=3µÐfS€
ÇÇ€FṂ÷9

Essayez-le en ligne!

Parcourt toutes les sous-listes contiguës, filtre pour ne garder que celles de longueur 3 et les sommes (qui vectorise) puis répète pour chaque liste résultante, pour obtenir les sommes des 3 sous-matrices 3 et finalement aplatit celles-ci en une seule liste, prend le minimum et divise par 9 (le nombre d'éléments faisant cette somme minimale).

Jonathan Allan
la source
J'aime l'idée des sous-listes de filtrage. Utile si cette taille de sous-liste dépend d'une valeur calculée.
miles
2

Pyth, 19 octets

chSsMsMs.:R3C.:R3Q9

Un programme qui prend l'entrée d'une liste de listes et imprime le résultat.

Suite de tests

Comment ça marche

[Explication à venir plus tard]

TheBikingViking
la source
1

Python 3 , 111 103 octets

lambda m,r=range:min(sum(sum(m[y+i][x:x+3])for i in r(3))/9for x in r(len(m[0])-3)for y in r(len(m)-3))

Essayez-le en ligne!

ovs
la source
1

Python 2, 96 octets

h=lambda a:[map(sum,zip(*s))for s in zip(a,a[1:],a[2:])]
lambda a:min(map(min,h(zip(*h(a)))))/9.

Cas de test chez Repl.it

Une fonction sans nom prenant une liste de listes, a - les lignes de la matrice.

La fonction d'assistance h zippe à travers trois tranches adjacentes et mappe la fonction de somme à travers la transposition zip(*s), de chacune. Cela se traduit par la somme de toutes les tranches de hauteur de trois colonnes simples.

La fonction sans nom appelle la fonction d'aide, transpose et appelle à nouveau la fonction d'aide sur le résultat, puis trouve le minimum de chacun et le minimum du résultat, qu'elle divise ensuite en 9.pour donner la moyenne.

Jonathan Allan
la source
1

JavaScript (ES6), 107 98 96 octets

Une fonction qui calcule les sommes des triplets sur les lignes, puis s'appelle pour faire la même chose sur les colonnes, en gardant une trace de la valeur minimale M.

f=m=>m.map((r,y)=>r.map((v,x)=>M=(z[x<<9|y]=v+=r[x+1]+r[x+2])<M?v:M),z=[M=1/0])&&m[1]?f([z]):M/9

JS est un peu bavard pour ce genre de choses et n'a pas de zip()méthode native . Il m'a fallu beaucoup de temps pour économiser une douzaine d'octets sur une approche plus naïve. (Pourtant, une méthode plus courte existe probablement.)

Version non récursive, 103 octets

Enregistré 2 octets avec l'aide de Neil

m=>m.map((r,y)=>y>1?r.map((v,x)=>[..."12345678"].map(i=>v+=m[y-i%3][x+i/3|0])&&(M=v<M?v:M)):M=1/0)&&M/9

Cas de test

Arnauld
la source
Je suis quelque peu intéressé par votre approche dite naïve, car le mieux que je puisse faire avec une approche raisonnablement pure était de 113 octets:(a,b=a.map(g=a=>a.slice(2).map((e,i)=>a[i]+a[i+1]+e)))=>eval(`Math.min(${b[0].map((_,i)=>g(b.map(a=>a[i])))})`)/9
Neil
@Neil Je pense que c'était quelque chose de proche m=>m.map((r,y)=>r.map((v,x)=>[..."12345678"].map(i=>v+=(m[y+i/3|0]||[])[x+i%3])&&(M=v<M?v:M)),M=1/0)&&M/9, même si je pense que ma première tentative était en fait plus grande que cela.
Arnauld
Nice, bien que j'ai pu raser un octet: m=>m.map((r,y)=>y>1&&r.map((v,x)=>[..."12345678"].map(i=>v+=m[y-i%3][x+i/3|0])&&(M=v<M?v:M)),M=1/0)&&M/9.
Neil
@Neil Cool. Cela permet d'économiser un octet de plus avecm=>m.map((r,y)=>y>1?r.map((v,x)=>[..."12345678"].map(i=>v+=m[y-i%3][x+i/3|0])&&(M=v<M?v:M)):M=1/0)&&M/9
Arnauld
1

05AB1E , 21 16 octets

2FvyŒ3ùO})ø}˜9/W

Essayez-le en ligne!

Explication

2F         }       # 2 times do:
  v     }          # for each row in the matrix
   yŒ3ù            # get all sublists of size 3
       O           # reduce by addition
         )ø        # transpose matrix
            ˜      # flatten the matrix to a list
             9/    # divide each by 9
               W   # get the minimum
Emigna
la source
1

Haskell , 87 octets

import Data.List
t(a:b:c:d)=a+b+c:t(b:c:d);t _=[]
s=(/9).minimum.(t=<<).transpose.map t

Essayez-le en ligne!

Roman Czyborra
la source