Parfois, lors de l'écriture de code brainfuck, vous ressentez le besoin de le rendre plus long que nécessaire pour encourager le débogage. Vous pourriez le faire en y insérant juste un ><
, mais quel plaisir est-ce? Vous aurez besoin de quelque chose de plus long et moins de NOPey pour confondre quiconque lit votre code.
Introduction rapide à Brainfuck
Brainfuck est un langage de programmation ésotérique créé en 1993 par Urban Müller, et remarquable pour son minimalisme extrême. (Wikipédia)
Brainfuck est un langage basé sur huit commandes: +-><,.[]
. Le code est exécuté sur quelque chose comme une machine de Turing: une bande infinie sur laquelle les valeurs peuvent être modifiées. Dans ce défi, nous nous concentrerons sur les quatre premiers:
+ increment the value at the pointer
- decrement the value at the pointer
> move the pointer right
< move the pointer left
NOP Brainfuck
Un brainfuck NOP est une séquence de personnages brainfuck qui, lorsqu'ils sont exécutés à partir de n'importe quel état, ne conduisent à aucun changement d'état. Ils se composent des quatre caractères mentionnés ci-dessus.
Le défi
Le défi consiste à écrire un programme ou une fonction qui, une fois exécuté, génère un NOP de brainfuck aléatoire de la longueur donnée.
Contribution
Vous recevrez en entrée un entier pair non négatif n
. (Les NOP sont impossibles à comprendre n
.)
Sortie
Vous produirez un NOP de brainfuck aléatoire de la longueur n
.
Règles
- La définition de NOP: lorsque la sortie du programme est insérée à tout moment dans un programme brainfuck, le comportement dudit programme ne doit en aucun cas changer. En d'autres termes, il ne doit pas changer l'état de l'interprète.
- Notez que, par exemple,
+>-<
est incorrect, car il modifie les valeurs des deux cellules sans les modifier en arrière. Veuillez tester votre solution pour ces derniers avant de poster. - Notez également qu'il
+>-<->+<
s'agit d'un NOP qui ne peut être réduit à rien simplement en le supprimant><
<>
+-
-+
. Ainsi, vous ne pouvez pas utiliser un algorithme qui les insère simplement les uns dans les autres.
- Notez que, par exemple,
- Chaque NOP valide de la longueur
n
doit avoir une chance non nulle d'apparaître dans la sortie. La distribution ne doit cependant pas être uniforme. - L'interprète brainfuck en question a une bande doublement infinie de cellules de précision arbitraire. Autrement dit, vous pouvez aller à l'infini dans les deux directions et incrémenter / décrémenter chaque cellule indéfiniment.
- Le programme doit se terminer en 1 minute pour
n
= 100 sur ma machine, donc pas de génération de tous les NOP possibles et d'en choisir un. - Si une entrée non valide (non entière, négative, impaire, etc.) est fournie, vous pouvez faire tout ce que vous souhaitez, y compris un crash.
Notation
Il s'agit de code-golf , donc la réponse la plus courte en octets l'emporte.
Exemples
Voici toutes les sorties valides pour n
= 4:
++-- +-+- +--+ --++ -+-+ -++-
>><< ><>< ><<> <<>> <><> <>><
><+- ><-+ <>+- <>-+
>+-< >-+< <+-> <-+>
+><- -><+ +<>- -<>+
+->< -+>< +-<> -+<>
Voici quelques sorties possibles pour n
= 20:
+>>->+<->-<<<->>++<<
>+>-<+<->+-<>->+<-<+
+--+-++--++-+--+-++-
>>>>>>>>>+-<<<<<<<<<
la source
+-<>
comme vous l'avez demandé:a
.
a un effet secondaire,,
écrase une valeur qui ne peut pas être récupérée sans l'utilisation de[]
. Mais[]
finira par définir une valeur à zéro. Cela écrase également une valeur (nous en aurions donc besoin d'une autre[]
pour la récupérer), sauf si nous pouvons être sûrs que la cellule affectée était zéro au départ. Cependant, nous devions rechercher une telle cellule avec quelque chose comme[>]
, et il est impossible de retourner de manière fiable à la position d'où nous venons.Réponses:
CJam,
6259 octetsMerci à nhahtdh pour avoir économisé 3 octets.
Parce qu'il n'y a aucune exigence pour une distribution particulière tant que chaque no-op apparaît avec une probabilité finie, nous pouvons simplifier cela beaucoup en générant simplement une chaîne contenant un nombre équilibré de
-+
et<>
, respectivement, en testant s'il s'agit d'un NOP et en le triant s'il le fait n'est pas.Bien sûr, pour des entrées plus longues, cela se traduira presque toujours par une sortie triée, mais vous pouvez tester le code avec une entrée comme
8
pour voir qu'il peut en principe produire n'importe quel NOP de la longueur donnée.Essayez-le en ligne.
la source
CJam,
118116 octetsCela est devenu un peu incontrôlable ... en particulier la seconde moitié semble être très jouable.
Testez-le ici.
Cela gère à
N = 100
peu près instantanément. Je n'ai pas le temps d'écrire la décomposition complète du code maintenant, voici donc l'algorithme:<
et>
avec une longueur aléatoire (paire) entre0
etN
inclus."<>><"
devient[0 '< -1 '> 0 '> 1 '< 0]
.N
.+-
à la chaîne d'une position aléatoire.Terminé. Ceci est basé sur l'observation que:
<
et>
pour remettre la tête de bande à sa position d'origine.En distribuant des quantités aléatoires mais équilibrées de
+
s et-
s entre tous les endroits où la tête de bande se trouve sur une cellule donnée, nous nous assurons de trouver tous les NOP possibles.la source
Mathematica, 350 octets
Bien trop long? Oui. Est-ce que je m'en soucie même? Pas avant que quelqu'un d'autre ne poste une réponse valide.
la source
+
.+
--
et<
->
paires jusqu'à ce que l'un soit un NOP. La moitié est prise par un simple interprète BF.Python 3 , 177 octets
Essayez-le en ligne!
J'ai utilisé le code de la réponse de Bubbler pour la simulation BF.
la source
Python 3 , 163 octets
Essayez-le en ligne!
Programme complet qui imprime les résultats sur STDOUT. La ligne qui exécute le code BF peut être jouable au golf.
Adopté l'approche de Tyilo; si le code BF généré n'est pas un NOP, jetez-le complètement et revenez à
'+-'
répété.la source
JavaScript (Node.js) , 160 octets
Essayez-le en ligne!
la source
Wolfram Language (Mathematica) , 224 octets
Essayez-le en ligne!
Voici la version non-golfée (ou plutôt pré-golfée):
Nous choisissons d'abord un nombre aléatoire de
<
«et>
» à utiliser, et générons une liste aléatoire avec un nombre égal de chacun.Pour remplir le reste des caractères, nous choisissons une position dans laquelle ajouter un
+
, puis trouvons une position où le pointeur pointe vers le même emplacement et y ajoutons un-
.Répétez l'opération jusqu'à ce que la liste ait une longueur
n
et chaînez le résultat.la source