Je génère un code à 6 chiffres des caractères suivants. Ceux-ci seront utilisés pour tamponner sur des autocollants.
Ils seront générés par lots de 10 000 ou moins (avant impression) et je n'envisage pas qu'il n'y aura jamais plus de 1-2 millions de dollars (probablement beaucoup moins).
Après avoir généré les lots de codes, je vérifierai la base de données MySQL des codes existants pour vous assurer qu'il n'y a pas de duplicate.
// exclude problem chars: B8G6I1l0OQDS5Z2 $characters = 'ACEFHJKMNPRTUVWXY4937'; $string = ''; for ($i = 0; $i < 6; $i++) { $string .= $characters[rand(0, strlen($characters) - 1)]; } return $string;
6 Réponses :
Vous auriez 21 codes ^ 6 = 85 766 121 ~ 85,8 strong> millions de codes! p>
Pour les générer (ce qui prendrait du temps), regardez la réponse sélectionnée à cette question: algorithme qui prendra des chiffres ou des mots et trouveront toutes les combinaisons possibles . P>
Vous vous mêlez de votre base et de votre exposant et vous avez gérée votre séparation du chiffre, c'est ~ 86 millions
21 ^ 6 = 85766121 Possibilités.
L'utilisation d'un dB et de stockage des valeurs utilisées est mauvaise. Si vous voulez simuler aléatoire, vous pouvez utiliser ce qui suit: p>
Réduisez à 19 numéros possibles et utilisez le fait que des groupes d'ordre p ^ k où p est un capitaine élevé sont toujours cycliques. P >
Prendre le groupe d'ordre 7 ^ 19, en utilisant un générateur co-prime à 7 ^ 19 (je choisirai 13 ^ 11, vous pouvez choisir tout ce qui n'est pas divisible de 7). P>
Alors Les travaux suivants: P>
$previous = 0; function generator($previous) { $generator = pow(13,11); $modulus = pow(7,19); //int might be too small $possibleChars = "ACEFHJKMNPRTUVWXY49"; $previous = ($previous + $generator) % $modulus; $output=''; $temp = $previous; for($i = 0; $i < 6; $i++) { $output += $possibleChars[$temp % 19]; $temp = $temp / 19; } return $output; }
Les codes générés doivent être stockés car ils sont associés à des timbres (produits) qui auront des informations associées à eux. Si je génère 10k de codes, alors un mois plus tard 10k, j'ai besoin de vérifier en quelque sorte qu'il n'y a pas de doublons dans ce nouveau lot de 10k.
J'ai posté comment ignorer les doublons, mais si vous stockez des informations supplémentaires de toute façon ignorant cette réponse.
@ Jean-Bernardpellerin php-ized You Code, espérons que cela ne vous dérange pas, veuillez vérifier si tout est allright
Cela sera-t-il unique à chaque fois ou dois-je vérifier cela manuellement? Et je ne veux pas que ce soit de 21 caractères seulement, tout va bien pour moi.
Comment utiliser cette réponse
6 ^ 19 ou 19 ^ 6? 6 n'est pas un peu d'impair, alors je suppose que vous vouliez dire ce dernier. Dans ce cas, votre choix de générateur n'est pas co-prime à celui-ci (19 ^ 11) - 11 ^ 19 semble ok. Je cherchais des codes de 5 caractères et je suis arrivé à cette réponse; J'utilise 23 ^ 5 (supprimé I, O et Q de l'alphabet) en tant que module et 19 ^ 11 pour le générateur qui semble fonctionner pour moi.
il devrait s'agir de $ de sortie. = $ Possisblecharks [$ TEMP% 19];
rand code> voir str_shauffe et aléatoire . li>
- Changer
rand code> à mt_rand code> li>
- Utilisez un stockage rapide comme
memcached code> ou redis code> pas mySQL lors de la vérification li>
possibilité totale p> xxx pré> 85,766,121 code> devrait être correct, pour ajouter de la base de données à cette génération Essayez: p> Exemple p> xxx pré> fonction utilisée p> xxx pré> ul>
Merci. 86 moulin suffit. Je vais utiliser votre suggestion de mt_rand. Je ne sais pas comment Memcached peut être utilisé pour vérifier que les codes dans un lot nouvellement généré n'existant pas déjà dans MySQL (contenant tous les lots de codes générés précédemment). À des fins d'impression, j'imagine générer des codes de 10k ou des codes à la fois
Comme Baba dit que générer une corde à la volée entraînera des tonnes de collisions. Plus vous allez passer à 80 millions de personnes déjà générées les plus difficiles qu'il deviendrai pour obtenir une chaîne disponible
Une autre solution pourrait être de générer toutes les combinaisons possibles une fois et de stocker chacune d'elles dans la base de données déjà, avec un champ de colonne booléen. qui marque si une rangée / jeton est déjà utilisée ou non p>
puis pour obtenir l'un d'entre eux p> puis marquez comme déjà utilisé p > UPDATE tokens SET tokenIsUsed = 1 WHERE token = ...
Merci, j'aurais pensé qu'il y aurait eu un coup de performance si vous conservez que 80 combinaisons de moulins, en termes de requêtes, etc. Le code sera recherché non seulement comme log.
Je pense que vous pourriez combiner cette approche avec la génération cyclique de @ Jean-Bernard et faire de votre requête beaucoup rapidement - remplissez la base de données avec toutes les combinaisons d'un ordre quelque peu aléatoire, et chaque fois que vous avez besoin de nouvelles valeurs, vous pouvez les saisir à un temps. Pourrait valoir un essai, de toute façon.
J'ai eu le même problème et j'ai trouvé une solution open source très impressionnante: p>
http://www.hashids.org/php/ p>
Vous pouvez le prendre et l'utiliser, il vaut également la peine de regarder dans son code source pour comprendre ce qui se passe sous la hotte. P>
ou ... Vous pouvez encoder le nom d'utilisateur + DateTime dans MD5 et enregistrer dans la base de données, ceci générera certainement un code unique;) P>
Il y a quelques bons messages ici sur diverses approches: Stackoverflow.com/questions/1846202/...
Si vous n'avez pas besoin de plus de 8 millions de codes et de codes courts et sans ambiguïtés, une priorité absolue, je dirais que vous avez un bon moyen de le faire.