Sortie de la spirale intérieure anti-horaire d'un réseau 2D


15

De cette question stackoverflow

Étant donné un tableau 2D de taille M×N , sortez les valeurs dans le sens inverse des aiguilles d'une montre. La sortie doit commencer de l'extérieur vers l'intérieur et le point initial sera toujours (0,0) .

Exemple donné:

[123456sept89dix111213141516]

Les valeurs de front dans le sens antihoraire sont alors 1,5,9,13,14,15,16,12,8,4,3,2 .

Maintenant, nous répétons le processus pour les valeurs intérieures. Cela se terminera par une matrice comme la suivante

[6septdix11]

Et les valeurs intérieures sont alors 6,dix,11,sept

Le résultat final sera alors 1,5,9,13,14,15,16,12,8,4,3,2,6,dix,11,sept


Règles

  • Supposons une entrée non vide
  • Supposons que les valeurs de la matrice sont des entiers positifs
  • Les méthodes d'E / S standard s'appliquent
  • Les règles de standard et les critères de victoire s'appliquent

Quelques cas de test

Input
[
  [1, 2, 3, 4, 5, 6, 7],
  [8, 9, 10,11,12,13,14],
  [15,16,17,18,19,20,21]
]
Output
1,8,15,16,17,18,19,20,21,14,7,6,5,4,3,2,9,10,11,12,13

--------------------------------------------------------

Input
[
    [1,2,3],
    [3,2,1],
    [4,5,6],
    [6,5,4],
    [7,8,9],
    [9,8,7]
]
Output
1,3,4,6,7,9,8,7,9,4,6,1,3,2,2,5,5,8

-----------------------------------------------------
Input
[
    [1]
]
Output
1
-----------------------------------
Input
[
    [1, 2],
    [2, 1]
]
Output
1,2,1,2
-----------------------------------------------------
Input
[
    [1,2,3,6,7],
    [2,4,3,2,1],
    [3,2,4,5,6],
    [6,5,6,5,4],
    [10,4,7,8,9],
    [12,4,9,8,7]
]
Output
1,2,3,6,10,12,4,9,8,7,9,4,6,1,7,6,3,2,4,2,5,4,7,8,5,5,2,3,4,6

Allons-nous donc dans le sens horaire ou antihoraire?
LegionMammal978

@ LegionMammal978 dans le sens inverse des aiguilles d'une montre (je pensais que cela s'appelait dans le sens inverse des aiguilles d'une montre)
Luis felipe De jesus Munoz

7
Les sens anti-horaire et anti-horaire sont tous les deux corrects, chacun étant plus commun en BrEng et AmEng, respectivement. Si vous voulez vraiment confondre, vous pouvez également utiliser des widdershins .
Digital Trauma

Réponses:


12

R , 54 octets

Plusieurs octets enregistrés par @Giuseppe et @ J.Doe.

f=function(m)if(ncol(m))c(m[,1],f(t(m[nrow(m):1,-1])))

Essayez-le en ligne!

Supprimez récursivement la première colonne et inversez / transposez la ligne (faisant de la ligne du bas la nouvelle première colonne) le reste de la matrice jusqu'à ce que vous vous retrouviez avec une seule colonne. Version "traditionnelle" non golfée:

f <- function(m) {
 if(ncol(m) == 1) {
    m
  } else {
    c(m[,1], f(t(m[nrow(m):1,-1])))
  }
}

Il a été souligné que l'on ncol(m)pouvait jouer au golf pour sum(m)enregistrer un autre octet car nous sommes autorisés à supposer des valeurs de matrice entières positives. Mais je vais le laisser comme ça car il fonctionne pour toutes les matrices (même les matrices de chaînes!)


Hou la la! J'adore la façon dont l'utilisation de t()empêche le drop=TRUEdéfaut `[`de gâcher la ifcondition!
Giuseppe

et divulgation complète, j'avais une solution d'environ 200 octets qui ne fonctionnait même pas, alors bravo à toi! Je vais probablement vous remettre une prime pour cela une fois que la question sera éligible à une prime.
Giuseppe

@Giuseppe de retour à 59 octets! J'ai été agréablement surpris t()de ne pas avoir à utiliser un is.nulltest qui faisait partie de mes tentatives initiales.
ngm

Ce dernier ne sera-t-il pas de mtoute façon nul, vous pouvez donc modifier l'instruction if pour 54 octets . Semble fonctionner pour les cas de test.
J.Doe


7

Pyth , 9 octets

shMM.utC_

Essayez-le ici!

Comment?

shMM.utC_     Full program. Takes a 2D array (matrix) from STDIN.
    .u        Until a result that has occurred before is found, loop and collect...
        _     Reverse the matrix (reverse the order of its rows).
       C      Transpose.
      t       Remove first element.
 hMM          For each element in the resulting 3D array, get the heads of its elements.
s             Flatten.

C'est super. En tant que débutant Pyth, je sais maintenant que j'ai beaucoup à apprendre,
ElPedro

5

Stax , 7 octets

ôQÖG·í<

Exécuter et déboguer

Il prend un tableau de lignes sur une ligne et produit une sortie séparée par des sauts de ligne.

Déballé, non golfé et commenté, il ressemble à ceci.

W       repeat the rest of the program until cancelled explicitly
  rM    rotate matrix *clock-wise* (yes, this is the opposite of the challenge)
  |c    assert matrix is truthy. (has rows) cancel otherwise.
  B     remove the top row of the matrix, and push separately to main stack
  rm    reverse the top row (this fixes the rotation direction), and print each value

Exécutez celui-ci


4

Pyth, 20 octets

J.TQWJ=+YhJ=J_.TtJ)Y

Essayez-le ici

Explication

J.TQWJ=+YhJ=J_.TtJ)Y
J.TQ                    Call the transposed input J.
    WJ            )     While J is not empty...
      =+YhJ             ... put the top row into Y (initially [])...
           =J   tJ      ... remove the top row...
             _.T        ... reverse and transpose (rotate clockwise).
                   Y    Output the result.

4

oK , 12 octets

*+,/(1_+|:)\

Essayez-le en ligne!

Cela abuse du fait que l'oK ne semble pas trop se soucier de la forme de la transposition. En k ce serait 13 octets : *:',/(1_+|:)\.

       +|:   /reverse, then transpose (rotate right)
     1_      /remove first line
    (     )\ /fixpoint of the above, keeping intermediate results (scan)
  ,/         /concatenate all the rows
*+           /get the first element of each row

3

Nettoyer , 69 octets

import StdEnv,StdLib
? =transpose
@[h:t]=h++ @(reverse(?t))
@_=[]

@o?

Essayez-le en ligne!

Déplace la ligne / colonne suivante en tête de la liste afin qu'elle puisse correspondre au modèle dans l'argument.

Pour le premier exemple du défi, cela ressemble à ceci:

@o? [[1, 2, 3, 4], [5, 6, 7, 8], [9, 10, 11, 12], [13, 14, 15, 16]]
@ h=:[1, 5, 9, 13] t=:[[2, 6, 10, 14], [3, 7, 11, 15], [4, 8, 12, 16]]
[1, 5, 9, 13] ++ @ h=:[14, 15, 16] t=:[[10, 11, 12], [6, 7, 8], [2, 3, 4]]
[1, 6, 9, 13, 14, 15, 16] ++ @ h=:[12, 8, 4] t=:[[11, 7, 3], [10, 6, 2]]
[1, 6, 9, 13, 14, 15, 16, 12, 8, 4] ++ @ h=:[3, 2] t=:[[7, 6], [11, 10]]
[1, 6, 9, 13, 14, 15, 16, 12, 8, 4, 3, 2] ++ @ h=:[6, 10] t=:[[7, 11]]
[1, 6, 9, 13, 14, 15, 16, 12, 8, 4, 3, 2, 6, 10] ++ @ h=:[11, 7] t=:[]
[1, 6, 9, 13, 14, 15, 16, 12, 8, 4, 3, 2, 6, 10, 11, 7] ++ @ []

3

Julia 0,7 , 47 octets

f(m)=[m[:,1];sum(m)<1?[]:f(rotr90(m[:,2:end]))]

Essayez-le en ligne!

Julia dispose d'une fonction intégrée pratique pour faire pivoter la matrice de 90 degrés, éliminant ainsi la nécessité d'opérations de transposition-inversion.

Comme vous pouvez le voir dans les avertissements du compilateur, il insiste sur le fait que tous les composants du conditionnel ternaire doivent être séparés par des espaces, et dans la version 1.0, cela a été effectivement appliqué.

Curieusement, dans cette situation, le moyen le plus court que j'ai trouvé pour sortir de la récursivité était d'utiliser un bloc try-catch:

Julia 1.0 , 50 octets

f(m)=[m[:,1];try f(rotr90(m[:,2:end]))catch;[]end]

Essayez-le en ligne!


2

JavaScript (Node.js) , 89 octets

f=a=>a>[]?[...a.map(x=>x[0]),...f(a[0].map((_,i)=>a.map(y=>y[i]).reverse()).slice(1))]:[]

Essayez-le en ligne!

Prend la première colonne, transpose la colonne restante, puis inverse chaque ligne (= fait pivoter la matrice de 90 degrés CW), puis répète jusqu'à ce que le tableau n'ait plus d'entrées.


2

APL (Dyalog) , 24 22 octets

{×≢⍵:⍵[;1],∇⍉⊖0 1↓⍵⋄⍬}

Essayez-le en ligne!

Comment?

{×≢⍵:⍵[;1],∇⍉⊖0 1↓⍵⋄⍬}
{                    } - a function
 ×≢⍵:                  - if non-empty:
     ⍵[;1]             - the left column
          ,∇⍉⊖0 1↓⍵    - repeat this function without the left column, rotated counter clockwise
                   ⋄⍬  - otherwise, return an empty vector

Une explication des opérateurs serait bien.
Arc676

1
@ Arc676, ajouté!
Zacharý

2

05AB1E , 13 11 10 octets

ΔRøćRˆ}¯˜þ

-2 octets grâce à @Emigna .

Essayez-le en ligne ou vérifiez tous les cas de test .

Explication:

Δ         # Loop until the stack no longer changes:
 R        #  Reverse the order of the rows
          #   i.e. [[1,2,3,4],[5,6,7,8],[9,10,11,12],[13,14,15,16]]
          #    → [[13,14,15,16],[9,10,11,12],[5,6,7,8],[1,2,3,4]]
  ø       #  Zip, swapping rows and column
          #   → [[13,9,5,1],[14,10,6,2],[15,11,7,3],[16,12,8,4]]
   ć      #  Head extracted
          #   → [[14,10,6,2],[15,11,7,3],[16,12,8,4]] and [13,9,5,1]
    R     #  Reverse this row
          #   → [1,5,9,13]
     ˆ    #  Pop and push it to the global array
}         # After the loop:
 ¯        #  Push the global array
          #   i.e. [[1,5,9,13],[14,15,16],[12,8,4],[3,2],[6,10],[11],[7],"",""]
  ˜       #  Flatten it
          #   → [1,5,9,13,14,15,16,12,8,4,3,2,6,10,11,7,"",""]
   þ      #  Remove all empty string by only leaving all digits
          #   → ["1","5","9","13","14","15","16","12","8","4","3","2","6","10","11","7"]
          # (and output it implicitly)


1

Fusain , 25 octets

≔⮌EA⮌ιθWθ«≔E§θ⁰⮌Eθ§μλθI⊟θ

Essayez-le en ligne! Le lien est vers la version détaillée du code. Explication:

≔⮌EA⮌ιθ

Faites pivoter l'entrée de 180 °. C'est pour deux raisons: a) la dernière ligne est la plus facile à supprimer, et b) il est plus facile de boucler si la ligne est supprimée à la fin de la boucle. (J'ai essayé de réfléchir et de produire dans le sens horaire, mais cela a pris un octet supplémentaire.)

Wθ«

Répétez jusqu'à ce que le tableau soit vide.

≔E§θ⁰⮌Eθ§μλθ

Faites pivoter le réseau de 90 °.

I⊟θ

Supprimez la dernière ligne du tableau et imprimez l'élément sous forme de chaînes sur des lignes distinctes.



1

PowerShell , 266 octets

Ouais .. PowerShell n'est pas le meilleur pour gérer les matrices. Mais, l'algorithme est fondamentalement le même que ci-dessus. Chaque ligne est représentée comme une chaîne séparée par des virgules, et nous faisons essentiellement une rotation et une transposition pour chaque couche. Je peux probablement me raser plus, mais ... je suis déjà en pyjama ...

Filter F{$a=$_-replace"],|]|\s",''-split'\['|?{$_-ne''};$b=@();while($a-ne $null){$N=($a[0]-split',').Count-1;$a=0..$N|%{$i=$_;($a|%{($_-split',')[$i]})-join','};if($d){[array]::Reverse($a)}if($N-gt0){$b+=$a[0];$a=$a[1..$N]}else{$b+=$a;$a=$null};$d=$true}$b-join','}

Essayez-le en ligne!

En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.