Donc, je prends ce que vous voulez est de produire une permutation de l'ensemble en utilisant le moins de mémoire possible.
Tout d'abord, cela ne peut pas être fait sans mémoire. Pour votre première chaîne, vous voulez une fonction qui pourrait produire l'une des chaînes avec une probabilité égale. Dites que cette fonction s'appelle nextString(). Si vous appelez à nouveau nextString() sans rien modifier dans l'état, bien sûr, il sera à nouveau capable de produire n'importe laquelle des chaînes.
Vous avez donc besoin de stocker quelque chose. La question est, qu'est-ce que vous avez besoin de stocker, et combien d'espace cela prendra-t-il?
Les chaînes peuvent être vues comme des nombres 0 - X^Y. (aaa = 0, aab = 1, aac = 2 ... aba = X ...) Donc, pour stocker une seule chaîne aussi efficacement que possible, vous auriez besoin de lg (X^Y) bits. Disons X = 16 et Y = 2. Ensuite, vous aurez besoin d'un octet de stockage pour spécifier une chaîne de façon unique.
Bien sûr, l'algorithme le plus naïf est de marquer chaque chaîne comme elle est produite, ce qui prend X^Y bits, qui dans mon exemple est de 256 bits (32 octets). C'est ce que vous avez dit que vous ne voulez pas faire. Vous pouvez utiliser un algorithme shuffle comme indiqué dans cette question: Creating a random ordered list from an ordered list (vous n'aurez pas besoin de stocker les chaînes comme vous les avez produites dans l'algorithme shuffle, mais vous devez les marquer). Ok, maintenant la question est, pouvons-nous faire mieux que cela? Combien avons-nous besoin de stocker, total?
Eh bien, au premier appel, nous n'avons pas besoin de stockage. Au deuxième appel, nous devons savoir lequel a été produit auparavant. Lors du dernier appel, nous avons seulement besoin de savoir lequel est le dernier. Donc, le pire est quand nous sommes à mi-chemin. Quand nous sommes à mi-chemin, il y a eu 128 chaînes produites, et il y en a 128 à faire. Nous devons savoir ce qu'il reste à produire. En supposant que le processus est vraiment aléatoire, toute scission est possible. Il y a (256 choisir 128) possibilités.Afin de potentiellement pouvoir stocker l'un de ceux-ci, nous avons besoin de lg (256 choisir 128) bits, qui selon google calculator est 251.67. Donc, si vous étiez vraiment intelligent, vous pourriez serrer l'information en 4 bits de moins que l'algorithme naïf. Probablement pas la peine.
Si vous voulez juste regarder randomish avec très peu de stockage, voir cette question: Looking for an algorithm to spit out a sequence of numbers in a (pseudo) random order
Pouvez-vous nous dire quels sont les besoins d'espace? Avez-vous des raisons de croire que le problème peut être résolu en utilisant moins de X à la puissance Y espace (et toujours garantir la résiliation)? –
Vous devez être plus précis sur "comment aléatoire" vous avez besoin d'être, et si vous avez vraiment besoin d'une permutation de la liste entière (toutes les entrées X^Y). – ShreevatsaR