Une chaîne régulière ressemble à ceci:
Hello,IAmAStringSnake!
Et un serpent à cordes ressemble à ceci:
Hel
l rin
o,IAmASt g
S
!ekan
Ta tâche
Les serpents de chaîne sont dangereux, vous devez donc créer un programme qui prend un serpent de chaîne en entrée et le sort en tant que chaîne normale.
Caractéristiques
- L'entrée peut être une chaîne multiligne ou un tableau de chaînes.
- Chaque ligne de l'entrée sera complétée d'espaces pour former une grille rectangulaire.
- Les personnages du serpent ne peuvent se connecter qu'aux personnages adjacents situés au-dessus, au-dessous, à gauche ou à droite (comme dans le jeu Snake). Ils ne peuvent pas aller en diagonale.
- Les personnages serpent ne seront jamais adjacents à une autre partie du serpent, mais uniquement aux personnages connectés.
- Le premier caractère de la chaîne est le caractère de fin avec la distance la plus courte entre Manhattan et le coin supérieur gauche de la grille de saisie (c’est-à-dire le nombre minimum de déplacements nécessaires pour qu’un serpent passe directement du caractère de fin à la partie supérieure gauche. Coin). Les deux extrémités n'auront jamais la même distance.
- La chaîne peut contenir n’importe quel caractère ASCII entre les points de code 33 et 126 inclus (sans espaces ni nouvelles lignes).
- La chaîne comportera entre 2 et 100 caractères.
- Le code le plus court en octets gagne.
Cas de test
(Grille d'entrée, suivie de la chaîne de sortie)
Hel
l rin
o,IAmASt g
S
!ekan
Hello,IAmAStringSnake!
----------
Python
Python
----------
P ngPu Code
r i z d G
o m z n o
gram lesA lf
ProgrammingPuzzlesAndCodeGolf
----------
~ zyx tsr XWVUTSR
}|{ wvu q Y Q
! p Z `ab P
"#$ 6789:; o [ _ c O
% 5 < n \]^ d N
('& 432 = m e M
) 1 > lkjihgf L
*+,-./0 ? K
@ABCDEFGHIJ
!"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~
----------
tSyrep
r p
in Sli
g Sile
Snakes n
Ser ylt
a eh ilS
fe w t
emo h
Sre
SlipperyStringSnakesSilentlySlitherSomewhereSafe
Réponses:
APL, 55 octets
Cette fonction prend une matrice de caractères contenant la chaîne serpent.
Exemple:
Explication:
(,⍵≠' ')/,⍳⍴⍵
: obtenir les coordonnées de tous les non-espaces(⊂0 0)
: commence à (0,0) (ce qui est une coordonnée invalide){
...}
: suivez le serpent, position donnée et serpent:1<⍴⍵:
: s'il reste plus d'un élément:∆←⍵~⍺
: supprime la position actuelle du serpent et la stocke dans∆
.+/¨|⍺-∆
: recherche la distance entre la position actuelle et chaque point du reste du serpent∆[⊃⍋...
] `: obtenir le point le plus proche sur le serpent∇
: exécutez à nouveau la fonction, avec le point le plus proche en tant que nouveau point actuel et le serpent raccourci en tant que nouveau serpent.⍺,
: ajoute la position actuelle au résultat de cette⋄⍺
: sinon, il suffit de retourner la position actuelle1↓
: supprime le premier élément du résultat (qui est la position (0,0))⍵[
...]
: récupère ces éléments de ⍵, dans cet ordrela source
JavaScript (ES6) + SnakeEx , 176 octets
Tu te souviens de SnakeEx? Bien, parce que moi non plus! Les suggestions de golf sont les bienvenues.
la source
MATL , 80 octets
Merci à @LevelRiverSt pour une correction
L'entrée se présente sous la forme d'un tableau 2D de caractères, avec des lignes séparées par
;
. Les cas de test dans ce format sontEssayez-le en ligne!
Explication
Les coordonnées de chaque caractère non-espace sont représentées par un nombre complexe. Pour chaque caractère actuel, le suivant est obtenu comme étant le plus proche (différence absolue minimale de leurs coordonnées complexes).
Pour déterminer le caractère initial, il faut trouver les deux extrémités. Cela se fait comme suit. Un point de terminaison est un caractère non-espace qui a exactement un voisin non-espace. Le nombre de voisins est obtenu par convolution 2D avec un masque approprié. Le point initial est le point final dont la coordonnée complexe a la plus petite somme de parties réelles et imaginaires; c'est-à-dire que, à Manhattan, la distance est la plus proche du nombre complexe 0 ou équivalente à 1 + 1j, qui est la coordonnée complexe du coin supérieur gauche.
la source
The initial point is the endpoint whose complex coordinate has the least absolute value
Attention: distance euclidienne! = Distance de Manhattan. par exemple, le point 7 + 7j a une distance euclidienne de 9,8994 et Manhattan une distance de 14. 10j est plus éloigné de la distance euclidienne mais considérablement plus proche de Manhattan. Autre que ça, super concept!C
198190179180181 181 octetsEdit: Utilisé le conseil par user81655 et supprimé la parenthèse dans l'opérateur ternaire, merci! J'ai également changé le test fastidieux (S & 1) pour l'uniformité pour le plus approprié (et plus court!) S% 2.
Edit2: L’utilisation intensive du style * a m’aveugle sur les optimisations évidentes de la définition de S, c’est-à-dire le remplacement de * (a + m) par un [m], etc. J'ai ensuite remplacé S lui-même par T, qui la moitié de ce que S fait. Le code tire également parti de la valeur de retour de putchar.
Edit3: Correction d'un bug qui existait depuis le début, le critère d'arrêt de recherche de Manhattan a <b + m n'est correct que si a a déjà été décrémenté. Cela ajoute 2 octets, mais on en retrouve un en rendant la définition de m globale.
Edit4: Mon golf a passé le minimum et va maintenant dans le mauvais sens. Une autre correction de bogue liée à la recherche Manhattan. J'avais initialement des contrôles entrants en place et sans ceux-ci, la recherche continue pour les grands tableaux d'entrée (quelque part autour de 50x50) au-delà du tableau b. Par conséquent, ce tableau doit être étendu à au moins deux fois la taille précédente, ce qui ajoute un octet supplémentaire.
Ungolfed et expliqué:
la source
a[1]
,a[-m]
etc, et en rendantm
global -m=103;main()
.C, 272 octets
Regardez la source de @ Zunga. Maintenant, regarde le mien. Vous voulez savoir comment j'ai obtenu les 91 octets supplémentaires?
Ungolfed:
la source
Python (2 et 3),
640 624 604 583 575 561 546538 octetsJe suis toujours un n00b de golf, donc c'est un peu gros.
Edit: Merci à @porglezomp pour les suggestions! Je n'ai pas supprimé tous les opérateurs 'et' car cela casserait Python 3.
Edit2: Merci à @Aleksi Torhamo pour le commentaire à propos de isspace (). La réduction résultante compense la correction de bogue que j’ai mise. Aussi, grâce à anonymous pour la coloration syntaxique!
Edit3: Merci à @ mbomb007 pour quelques octets supplémentaires.
Et voici ma version pré-golf
la source
S=lambda s:s.isspace()
puis en faisant à laS(s)
place des.isspace()
.and
à<
, depuisf() < g() < h()
est la même que celleg = g(); f() < g and g < h()
en termes d'effets secondaires (chaînes de comparaison de court-circuit), et vous ne tenez pas compte du résultat des comparaisons de toute façon.m[(x,y)]=
est le même que le plus courtm[x,y]=
S=str.isspace
S
et utiliser<'!'
à la place dans chaque occurrence peut être de la même longueur, ouvrant éventuellement une opportunité d'économiser davantage. Changerif 1-S(v[x]):
pourif(v[x]<'!')<1:
, par exemple. Et peut-être que vous pourriez supprimer certaines parenthèses lors des comparaisons ultérieures en procédant ainsi.JavaScript (ES6), 195
Voir l'explication à l'intérieur de l'extrait de test
Tester
la source
););}
nécessaires?for
tête où 2 points sont nécessaires. Le second est le séparateur pour lefor
corpsLua,
562535529513507504466458 octetsDe loin mon golf le plus massif en ce moment,
je pense que je peux encore couper 100 octets, ce sur quoi je vais travailler, mais je l’afficherai comme réponse car cela prenait déjà un peu de temps :).J'avais raison, j'ai coupé plus de 100 octets! Je ne pense pas qu'il y ait beaucoup de place à l'amélioration.cette fonction doit être appelée avec un tableau 2D contenant un caractère par cellule.
Sauvegardé 40 octets en travaillant avec @KennyLau , merci à lui!
Woohoo! Moins de 500!
Ungolfed
Les explications viendront une fois que j'aurai fini de jouer au golf. Pour le moment, je vais vous prêter une version lisible de ce code source: DVoici les explications!Edit: pas mis à jour avec la dernière modification, toujours jouer au golf avant la mise à jour. Idem pour les explications
Voici donc quelques explications détaillées sur le fonctionnement de ce programme.
Tout d'abord, considérons la boucle étiquetée
a
, elle nous permet de trouver l'extrémité la plus proche du coin supérieur gauche. Il y aura une boucle pour toujours s'il n'y a pas de fin, mais ce n'est pas un problème: D.Sur une grille 4x4, voici les distances des serpents (à gauche), et leur ordre d'affichage (à droite)
Pour chacun de ces personnages, pour être la fin, il doit vérifier deux conditions: - ne pas être un espace - être entouré exactement par 3 espaces (ou exactement 1 non-espace)
Ces conditions sont vérifiées dans le code suivant
Vérifier si le caractère n'est pas un espace est obtenu par l'expression
m[i][j]~=s
.En vérifiant si nous sommes entourés par seulement un espace non-espace, en remplissant les conditions ci-dessus pour notre environnement, vous pouvez écrire ceci:
Et enfin, si tout ce qui précède est évalué comme étant vrai, le ternaire retournera ce qui se trouve dans le dernier
and
->m[i][j]
. Sinon, nous laissonsr
hors service :)Maintenant que nous avons la tête du serpent, allons jusqu'au bout! La itération du serpent est principalement réalisée par les ternaires imbriqués suivants:
Nous sommes-ensemble
i
etj
en même temps pour éviter les mannequins qui nécessitent garder les anciennes valeurs Ils ont tous deux la même structure exacte et les conditions d' usage simples, donc je vais les présenter sous la forme d'imbriquéeif
, il devrait vous permettre de les lire plus facilement. :)Peut être traduit en:
Essaye-le!
Voici le code que j'utilise pour exécuter ceci, vous pouvez le tester en ligne en le copiant-collant.
la source
Lua, 267 octets
Lua 5.3 est requis.
Usage:
la source
Python 3,
245243241236 octetss
est la chaîne d'entrée,n
la sortie est-elle imprimée sur stdout:Edit: Merci à @Cees Timmerman pour la sauvegarde de 5 octets!
la source
c>' 'and
etprint n
en Python 2.if
au lieu deelif
?s
variable @ Qwerp-Derp est une chaîne multiligne; le dernier caractère de la chaîne doit être une nouvelle ligne (cela est nécessaire pour réussir lePython
test)Python, 537
Ma solution initiale:
Compacté un peu, mais laissé comme méthode:
la source
Java 7,
927924923 octetsOk, ça a pris un peu de temps .. Dans certains langages de programmation, peu importe que votre tableau x et y se trouvent en dehors des limites d'un tableau 2D, mais avec Java cela jette
ArrayIndexOutOfBoundsExceptions
, tout doit être vérifié ..Je détermine d'abord le point de départ, puis utilise une méthode récursive pour construire la chaîne à partir de là. De plus, j'utilise une liste pour garder une trace des coordinations que j'ai déjà rencontrées, ainsi elle ne passera pas dans une boucle de va-et-vient en boucle (donnant ainsi une exception StackOverflowException).
C’est probablement la réponse la plus longue que j’ai publiée jusqu’à présent, mais bien que certaines parties puissent être jouées au golf, je ne pense pas que ce défi puisse être beaucoup plus court en Java. Java ne convient tout simplement pas pour suivre un chemin dans une grille. C'était quand même un défi amusant à comprendre. :)
Ungolfed & cas de test:
Essayez ici.
Sortie:
la source
PHP,
199184182 octetspeut encore avoir un peu de potentiel de golf
prend l'entrée en tant que chaîne multiligne à partir de la ligne de commande, attend les sauts de ligne de style linux.
Run
php -r '<code>' '<string>'
; échapper à la ligne.panne
la source
C #, 310
(Edit: correction de bug)
Une fonction avec un paramètre de chaîne multiligne renvoyant une chaîne.
Y compris le demandé
using
dans le nombre d'octets.Ceci est un portage de ma réponse javascript.
Test sur ideone
Avec des espaces
la source
Python 2, 251 octets
Ou, si vous souhaitez diriger les nouvelles lignes dans vos tests, 257 octets:
Passe tous les tests.
Résulte en:
la source
b.append(...)
parb+=[...]
etdef n(x,y):return ...
avecn=lambda x,y:...
' '
.~-x
au lieu dex-1
, vous n’aurez pas à utiliser de parenthèses.Japt
-P
, 106 octetsEssayez-le en ligne!
C'est ... euh ... une abomination.
Déballé et comment ça marche
Un point remarquable est que j’ai utilisé la priorité des opérateurs entre les opérateurs assignation et les opérateurs de virgule dans JS, afin de compresser certaines lignes et de conserver le raccourci
@
(XYZ{
) utilisable.la source