Cette question est basée sur les tours de puzzle de placement de numéros (également connues sous le nom de gratte-ciel), que vous pouvez jouer en ligne . Votre objectif est de trouver une solution au puzzle et de déterminer les indices - le nombre de tours visibles le long de chaque ligne et colonne. C'est le golf de code, donc le moins d'octets gagne.
Fonctionnement des tours
La solution à un casse - tête Towers est un carré latin - une n*n
grille dans laquelle chaque ligne et colonne contient une permutation des nombres 1
par n
. Un exemple pour n=5
est:
4 3 5 2 1
5 4 1 3 2
1 5 2 4 3
2 1 3 5 4
3 2 4 1 5
Chaque ligne et colonne est étiquetée avec un indice à chaque extrémité comme:
2 3 1 4 5
v v v v v
2 > 4 3 5 2 1 < 3
1 > 5 4 1 3 2 < 4
2 > 1 5 2 4 3 < 3
3 > 2 1 3 5 4 < 2
3 > 3 2 4 1 5 < 1
^ ^ ^ ^ ^
2 2 2 2 1
Chaque indice est un nombre de 1
à n
qui vous indique le nombre de tours que vous "voyez" en regardant le long de la ligne / colonne de cette direction, si les nombres sont traités comme des tours de cette hauteur. Chaque tour bloque des tours plus courtes derrière elle. En d'autres termes, les tours que vous pouvez voir sont celles qui sont plus hautes que n'importe quelle tour avant elles.
Par exemple, regardons la première ligne.
2 > 4 3 5 2 1 < 3
Il a un indice de 2
gauche parce que vous pouvez voir le 4
et le 5
. Le 4
bloque la 3
vue et 5
bloque tout le reste. De la droite, vous pouvez voir des 3
tours: 1
, 2
et 5
.
Exigences du programme
Écrivez un programme ou une fonction qui prend dans la grille des nombres et des sorties ou imprime les indices, dans le sens horaire à partir du coin supérieur gauche.
Contribution
Un n*n
carré latin avec 2<=n<=9
.
Le format est flexible. Vous pouvez utiliser n'importe quelle structure de données qui représente une grille ou une liste contenant des nombres ou des caractères numériques. Vous pouvez avoir besoin d'un séparateur entre les lignes ou pas de séparateur du tout. Certaines possibilités sont une liste, une liste de listes, une matrice, une chaîne séparée par jeton comme
43521 54132 15243 21354 32415,
ou une chaîne sans espaces.
Vous n'êtes pas donné n
dans le cadre de l'entrée.
Sortie
Retournez ou imprimez les indices en partant du coin supérieur gauche et dans le sens des aiguilles d'une montre. Donc, d'abord les indices supérieurs lisant vers la droite, puis les indices droits lisant vers le bas, puis les indices inférieurs lisant vers la gauche, les indices gauches lisant vers le haut.
Ce serait 23145 34321 12222 33212
pour l'exemple précédent
2 3 1 4 5
v v v v v
2 > 4 3 5 2 1 < 3
1 > 5 4 1 3 2 < 4
2 > 1 5 2 4 3 < 3
3 > 2 1 3 5 4 < 2
3 > 3 2 4 1 5 < 1
^ ^ ^ ^ ^
2 2 2 2 1
Tout comme pour l'entrée, vous pouvez utiliser une liste, une chaîne ou toute structure ordonnée. Les quatre "groupes" peuvent être séparés ou non, dans une structure imbriquée ou plate. Mais, le format doit être le même pour chaque groupe.
Exemples de cas de test:
(Votre format d'entrée / sortie ne doit pas nécessairement être le même que ceux-ci.)
>> [[1 2] [2 1]]
[2 1]
[1 2]
[2 1]
[1 2]
>> [[3 1 2] [2 3 1] [1 2 3]]
[1 2 2]
[2 2 1]
[1 2 3]
[3 2 1]
>> [[4 3 5 2 1] [5 4 1 3 2] [1 5 2 4 3] [2 1 3 5 4] [3 2 4 1 5]]
[2 3 1 4 5]
[3 4 3 2 1]
[1 2 2 2 2]
[3 3 2 1 2]
>> [[2 6 4 1 3 7 5 8 9] [7 2 9 6 8 3 1 4 5] [5 9 7 4 6 1 8 2 3] [6 1 8 5 7 2 9 3 4] [1 5 3 9 2 6 4 7 8] [3 7 5 2 4 8 6 9 1] [8 3 1 7 9 4 2 5 6] [9 4 2 8 1 5 3 6 7] [4 8 6 3 5 9 7 1 2]]
[4 2 2 3 3 3 3 2 1]
[1 3 3 2 2 2 2 3 3]
[4 3 2 1 2 3 3 2 2]
[3 1 2 4 3 3 2 2 5]
Pour votre commodité, voici les mêmes cas de test dans un format de chaîne plate.
>> 1221
21
12
21
12
>> 312231123
122
221
123
321
>> 4352154132152432135432415
23145
34321
12222
33212
>> 264137589729683145597461823618572934153926478375248691831794256942815367486359712
422333321
133222233
432123322
312433225
≢¨∪¨↓⌈\(⍉⍪⌽⍪⍉∘⌽∘⊖⍪⊖)
Python 2, 115 octets
Il y a énormément de listes inversées en cours.
Prend l'entrée comme une liste imbriquée (par exemple, appelez avec
T([[4,3,5,2,1],[5,4,1,3,2],[1,5,2,4,3],[2,1,3,5,4],[3,2,4,1,5]])
). La sortie est une seule liste plate.Non golfé:
Variante 115:
Je ne sais pas pourquoi cela fonctionne avec une compréhension de liste, mais jette un
NameError
avec une compréhension d'ensemble ...Un peu trop long, mais si quelqu'un est intéressé - oui, il est possible de le ramener à un lambda!
Pyth , 25 octets
Port Pyth obligatoire.
Entrez la liste via STDIN, par exemple
[[4, 3, 5, 2, 1], [5, 4, 1, 3, 2], [1, 5, 2, 4, 3], [2, 1, 3, 5, 4], [3, 2, 4, 1, 5]]
.Essayez-le en ligne ... c'est ce que je dirais mais malheureusement, pour des raisons de sécurité, l'interpréteur en ligne interdit l'utilisation d'eval sur des crochets imbriqués. Essayez
JcQ5V4=J_CJ~Yml{meS<dhkUd_J)Y
plutôt le code de contournement et saisissez-le comme une liste aplatie comme[4, 3, 5, 2, 1, 5, 4, 1, 3, 2, 1, 5, 2, 4, 3, 2, 1, 3, 5, 4, 3, 2, 4, 1, 5]
.(Merci à @isaacg qui a aidé à jouer au golf quelques octets)
la source
<
et>
sont les opérateurs de tranche unilatérale, ils:d0hk
peuvent donc être transformés en<dhk
.U
sur les entrées de collecte est identique àUl
, doncUld
peut être transformé enUd
.CJam,
2927 octetsEntrée comme
Sortie comme
Comment ça marche
L'idée de base est de faire travailler le code le long des lignes et de faire pivoter la grille dans le sens antihoraire 4 fois. Pour compter les tours, j'élève chaque tour dans la mesure où cela ne fait pas de "différence visuelle" (c'est-à-dire, ne la changez pas si elle est visible, ou ne la tirez pas à la même hauteur de la tour devant il), puis je compte des hauteurs distinctes.
la source
APL, 44
Testé ici.
la source
J, 35 caractères
Exemple:
Essayez-le ici.
la source
Haskell, 113
la source
Mathematica,
230,120,116,113110 octetsUsage:
la source
a[[y]][[x]]
esta[[y,x]]
. Et l'utilisationArray
pourrait être plus courte queTable
.JavaScript,
335264256213Évaluez dans la console JavaScript du navigateur (j'ai utilisé Firefox 34.0, ne semble pas fonctionner dans Chrome 39 ??) Testez avec:
Voici l'incarnation actuelle du code non golfé - il devient plus difficile à suivre:
Je n'ai intentionnellement regardé aucune des autres réponses, je voulais voir si je pouvais trouver quelque chose moi-même. Mon approche consistait à aplatir les tableaux d'entrée en un tableau unidimensionnel et à précalculer les décalages vers les lignes dans les quatre directions. Ensuite, j'ai utilisé shift right pour tester si la prochaine tour était fausse et si c'était le cas, puis incrémenter le compteur pour chaque ligne.
J'espère qu'il existe de nombreuses façons d'améliorer cela, peut-être pas de précalculer les décalages, mais plutôt d'utiliser une sorte de débordement / modulo sur le tableau d'entrée 1D? Et peut-être combiner mes boucles, devenir plus fonctionnel, dédupliquer.
Toute suggestion serait appréciée!
Mise à jour # 1 : Progrès, nous avons la technologie! J'ai pu me débarrasser des décalages précalculés et les faire en ligne avec des opérateurs ternaires enchaînés. J'ai également pu me débarrasser de mon instruction if et convertir les boucles for en whiles.
Mise à jour # 2 : C'est assez frustrant; pas de pizza pour moi. Je pensais que devenir fonctionnel et utiliser la récursion raserait de nombreux octets, mais mes premiers essais ont fini par être plus gros de 100 caractères! En désespoir de cause, je suis allé à fond sur l'utilisation des fonctions de flèche de graisse ES6 pour vraiment le réduire. Ensuite, je me suis mis à remplacer les opérateurs booléens par des opérateurs arithmétiques et à supprimer les parens, les points-virgules et les espaces partout où je pouvais. J'ai même arrêté de déclarer mes vars et pollué l'espace de noms global avec mes symboles locaux. Sale, sale. Après tout cet effort, j'ai battu mon score de mise à jour # 1 par un énorme 8 caractères, jusqu'à 256. Blargh!
Si j'appliquais les mêmes optimisations impitoyables et astuces ES6 à ma fonction de mise à jour # 1, je battrais ce score d'un mile. Je peux faire une mise à jour # 3 juste pour voir à quoi cela ressemblerait.
Mise à jour # 3 : Il s'avère que l'approche récursive de la grosse flèche avait beaucoup plus de vie, j'avais juste besoin de travailler directement avec l'entrée bidimensionnelle plutôt que de l'aplatir et de mieux exploiter les portées de fermeture. J'ai réécrit les calculs de décalage du tableau interne deux fois et j'ai obtenu le même score, donc cette approche est peut-être proche d'être minée!
la source
Java, uniquement
352350325 octets ...Entrée comme
43521 54132 15243 21354 32415
Sortie comme:
23145343211222233212
Dentelé:
Tous les conseils seraient grandement appréciés!
la source
for
bouclesfor(;i<n;i++)
àfor(;++i<n;)
et initialiseri
à-1
. Ensuite, utilisez-les pour faire des choses. Vous pouvez également faire de même avec l'autre boucle.a[i].charAt(j)-'0'
au lieu d'une analyse explicite. Cela ne nécessite pas non plus de délimiteurs dans l'entrée (rend le format d'entrée plus semblable au format de sortie).for
-loops, vous pouvez toujours placer quelque chose d'utile dans la partie "incrément de boucle". Cela rend le code plus obscur et supprime un point-virgule. Par exemple:for(j=n;j-->0;System.out.print(c))
.Python 2 - 204 octets
C'est probablement un golf vraiment médiocre. Je pensais que le problème était intéressant, alors j'ai décidé de le résoudre sans regarder la solution de quelqu'un d'autre. En tapant cette phrase, je n'ai pas encore examiné les réponses à cette question. Je ne serais pas surpris si quelqu'un d'autre a déjà fait un programme Python plus court;)
Exemple d'E / S
Vous pouvez éventuellement inclure des espaces dans l'entrée. À peu près n'importe où, honnêtement. Tant que vous le pouvez
eval()
, cela fonctionnera.Explication
La seule partie intéressante de ce programme est la première ligne. Il définit une fonction
f(l)
qui vous indique combien de tours peuvent être vues dans une rangée, et le reste du programme applique simplement cette fonction à chaque position possible.Lorsqu'il est appelé, il trouve la longueur de
l
et l'enregistre dans une variablen
. Ensuite, il crée une nouvelle variablek
avec cette compréhension de liste assez monstrueuse:Ce n'est pas trop mal quand vous le décomposez. Depuis
n==len(l)
, tout ce qui précèdeif
représente justel
. Cependant, en utilisantif
nous pouvons supprimer certains éléments de la liste. Nous construisons une liste avec([0]+list(l))
, qui est juste "l
avec un0
ajout au début" (ignorez l'appel àlist()
, ce n'est là que parce qu'il y a parfoisl
un générateur et nous devons nous assurer qu'il s'agit bien d'une liste ici).l[c]
n'est mis dans la liste finale que s'il est supérieur à([0]+list(l))[c]
. Cela fait deux choses:l[c]
devientc+1
. Nous comparons efficacement chaque élément à l'élément à gauche de celui-ci. Si c'est plus, c'est visible. Sinon, il est masqué et supprimé de la liste.[0]+
non - sens et juste comparél[c]
àl[c-1]
, Python comparerait la première tour à la dernière (vous pouvez indexer dans une liste à partir de la fin avec-1
,-2
etc.), donc si la dernière tour était plus grand que la premier nous obtiendrions le mauvais résultat.En fin de compte,
l
contient un certain nombre de tours etk
contient chacune de celles qui ne sont pas plus courtes que son voisin immédiat à gauche. Si aucun d'entre eux ne l'était (par exemple pourf([1,2,3,4,5])
), alorsl == k
. Nous savons qu'il n'y a plus rien à faire et à retournern
(la longueur de la liste). Sil != k
, cela signifie qu'au moins une des tours a été supprimée cette fois-ci et il peut y avoir plus à faire. Donc, nous revenonsf(k)
. Dieu, j'aime la récursivité. Fait intéressant,f
récursive toujours un niveau plus profond que strictement "nécessaire". Lorsque la liste qui sera retournée est générée, la fonction n'a aucun moyen de le savoir au début.Lorsque j'ai commencé à écrire cette explication, ce programme faisait 223 octets. En expliquant les choses, j'ai réalisé qu'il y avait des moyens de sauver des personnages, donc je suis content d'avoir tapé ça! Le plus grand exemple est celui qui
f(l)
a été implémenté à l'origine comme une boucle infinie qui a été rompue lorsque le calcul a été effectué, avant que je ne réalise que la récursivité fonctionnerait. Cela montre simplement que la première solution à laquelle vous pensez ne sera pas toujours la meilleure. :)la source
Matlab,
(123)(119)utilisé comme ceci:
C #, jusqu'à 354 ...
Approche différente de celle utilisée par TheBestOne.
la source
\n
au lieu de nouvelles lignes, je viens de les remplacer par des espaces, donc le code s'exécute immédiatement lorsque quelqu'un le copie. Et je me suis permis de supprimer le dernierend
(qui ferme la fonction, ce qui n'est pas nécessaire) qui enregistre 4 caractères supplémentaires, j'espère que c'était ok =)end
cependant, thx :)