Random Six Character Strings Without Collisions
I want to generate a random list of six characters that only contain characters from "0...9" and "A...Z".
For this I can define
ToCharacterCode[{"ABCDEFGHIJKLMONPQRSTUVWXYZ", "0123456789"}]
I can modify the answer here as
rndnew = FromCharacterCode@
RandomChoice[Join @@ Range[{48, 65}, {57, 90}], #] &
I can now generate five of these strings by doing
rndnew[{5, 6}]
This results in something like
{"35UVUS", "F7WIJG", "PQSBHF", "PIHTSW", "R3MDM6"}
My question is how can I guarantee that these strings have no collisions (I know this is a very large space)? Is there a better way to code this using random over the range of the size of this set (like a linear congruential generator with that range) to make sure the strings are unique or is there a facility in Mathematica to do that?
list-manipulation random
add a comment |
I want to generate a random list of six characters that only contain characters from "0...9" and "A...Z".
For this I can define
ToCharacterCode[{"ABCDEFGHIJKLMONPQRSTUVWXYZ", "0123456789"}]
I can modify the answer here as
rndnew = FromCharacterCode@
RandomChoice[Join @@ Range[{48, 65}, {57, 90}], #] &
I can now generate five of these strings by doing
rndnew[{5, 6}]
This results in something like
{"35UVUS", "F7WIJG", "PQSBHF", "PIHTSW", "R3MDM6"}
My question is how can I guarantee that these strings have no collisions (I know this is a very large space)? Is there a better way to code this using random over the range of the size of this set (like a linear congruential generator with that range) to make sure the strings are unique or is there a facility in Mathematica to do that?
list-manipulation random
5
replaceRandomChoice
withRandomSample
?
– kglr
Dec 13 '18 at 14:20
@kglr: I will certainly look into that. Thanks for the pointer!
– Moo
Dec 13 '18 at 14:21
2
When a function is close to what you want, look at theSee Also
section of that function's documentation.
– Bob Hanlon
Dec 13 '18 at 14:39
Sorry that I'm not a Mathematica user, so just provide my thought on solving this in pseudo code: while less than 5 strings in the collection: generate a random string if new string already exists in the collection: do nothing else: add it to the collection No collisions guaranteed, but might take a while.
– Kyle R.
Dec 14 '18 at 0:41
add a comment |
I want to generate a random list of six characters that only contain characters from "0...9" and "A...Z".
For this I can define
ToCharacterCode[{"ABCDEFGHIJKLMONPQRSTUVWXYZ", "0123456789"}]
I can modify the answer here as
rndnew = FromCharacterCode@
RandomChoice[Join @@ Range[{48, 65}, {57, 90}], #] &
I can now generate five of these strings by doing
rndnew[{5, 6}]
This results in something like
{"35UVUS", "F7WIJG", "PQSBHF", "PIHTSW", "R3MDM6"}
My question is how can I guarantee that these strings have no collisions (I know this is a very large space)? Is there a better way to code this using random over the range of the size of this set (like a linear congruential generator with that range) to make sure the strings are unique or is there a facility in Mathematica to do that?
list-manipulation random
I want to generate a random list of six characters that only contain characters from "0...9" and "A...Z".
For this I can define
ToCharacterCode[{"ABCDEFGHIJKLMONPQRSTUVWXYZ", "0123456789"}]
I can modify the answer here as
rndnew = FromCharacterCode@
RandomChoice[Join @@ Range[{48, 65}, {57, 90}], #] &
I can now generate five of these strings by doing
rndnew[{5, 6}]
This results in something like
{"35UVUS", "F7WIJG", "PQSBHF", "PIHTSW", "R3MDM6"}
My question is how can I guarantee that these strings have no collisions (I know this is a very large space)? Is there a better way to code this using random over the range of the size of this set (like a linear congruential generator with that range) to make sure the strings are unique or is there a facility in Mathematica to do that?
list-manipulation random
list-manipulation random
asked Dec 13 '18 at 14:17
Moo
7011515
7011515
5
replaceRandomChoice
withRandomSample
?
– kglr
Dec 13 '18 at 14:20
@kglr: I will certainly look into that. Thanks for the pointer!
– Moo
Dec 13 '18 at 14:21
2
When a function is close to what you want, look at theSee Also
section of that function's documentation.
– Bob Hanlon
Dec 13 '18 at 14:39
Sorry that I'm not a Mathematica user, so just provide my thought on solving this in pseudo code: while less than 5 strings in the collection: generate a random string if new string already exists in the collection: do nothing else: add it to the collection No collisions guaranteed, but might take a while.
– Kyle R.
Dec 14 '18 at 0:41
add a comment |
5
replaceRandomChoice
withRandomSample
?
– kglr
Dec 13 '18 at 14:20
@kglr: I will certainly look into that. Thanks for the pointer!
– Moo
Dec 13 '18 at 14:21
2
When a function is close to what you want, look at theSee Also
section of that function's documentation.
– Bob Hanlon
Dec 13 '18 at 14:39
Sorry that I'm not a Mathematica user, so just provide my thought on solving this in pseudo code: while less than 5 strings in the collection: generate a random string if new string already exists in the collection: do nothing else: add it to the collection No collisions guaranteed, but might take a while.
– Kyle R.
Dec 14 '18 at 0:41
5
5
replace
RandomChoice
with RandomSample
?– kglr
Dec 13 '18 at 14:20
replace
RandomChoice
with RandomSample
?– kglr
Dec 13 '18 at 14:20
@kglr: I will certainly look into that. Thanks for the pointer!
– Moo
Dec 13 '18 at 14:21
@kglr: I will certainly look into that. Thanks for the pointer!
– Moo
Dec 13 '18 at 14:21
2
2
When a function is close to what you want, look at the
See Also
section of that function's documentation.– Bob Hanlon
Dec 13 '18 at 14:39
When a function is close to what you want, look at the
See Also
section of that function's documentation.– Bob Hanlon
Dec 13 '18 at 14:39
Sorry that I'm not a Mathematica user, so just provide my thought on solving this in pseudo code: while less than 5 strings in the collection: generate a random string if new string already exists in the collection: do nothing else: add it to the collection No collisions guaranteed, but might take a while.
– Kyle R.
Dec 14 '18 at 0:41
Sorry that I'm not a Mathematica user, so just provide my thought on solving this in pseudo code: while less than 5 strings in the collection: generate a random string if new string already exists in the collection: do nothing else: add it to the collection No collisions guaranteed, but might take a while.
– Kyle R.
Dec 14 '18 at 0:41
add a comment |
4 Answers
4
active
oldest
votes
Just changing RandomChoice
to RandomSample
doesn't help, since RandomSample
just means that none of the characters are repeated, and clearly you want to allow repeated characters, since one of your strings is "35UVUS". One idea is to oversample and remove duplicates. For example:
SeedRandom[1]
Take[
DeleteDuplicates[rndnew[{10, 6}]],
UpTo[5]
]
{"K1263G", "SXVXHC", "UO2PBL", "EC1FTJ", "0TKLEH"}
Another possibility is to index the possible random strings, and then do a random sample from the possible indices. For your case, the number of possible strings is simply 36^6. To convert from an index to a string:
characters = Join[CharacterRange["A","Z"], CharacterRange["0","9"]];
fromIndex[index_, len_] := StringJoin[
characters[[1+IntegerDigits[index, 36, len]]]
]
Then, a function that returns n
samples of length len
strings:
sample[n_, len_] := fromIndex[#, len]& /@ RandomSample[1 ;; 36^len, n]
Example:
SeedRandom[1]
sample[5, 6]
{"0621O7", "0WH6XW", "ODLV4Z", "KWSN6U", "AMOSFA"}
Is there a way to generate some number of these, keep the state of the RNG and use it to reseed from that point moving forward so we can maintain uniqueness of all six-characters over time?
– Moo
Dec 13 '18 at 16:18
@Moo Not that I'm aware of. Do you know how many unique strings you want in total?
– Carl Woll
Dec 13 '18 at 16:49
If I am doing my math correctly, we have 6-character strings where strings can repeat, then there are $26$ letters plus $10$ digits in the pool of characters, giving us $36$ in all per character. This means we would have $36^6 = 2176782336$ combinations.
– Moo
Dec 13 '18 at 16:52
1
@Moo There are 36^6 total strings, but how many do you want to generate? There is no point in using a random approach if you want to generate all of them.
– Carl Woll
Dec 13 '18 at 17:04
CarlWoll: The issue is that I would generate something like $10000$ at a time, use them and then generate a new batch and over time, duplicates matter. Maybe there is a better way based on that, but I haven't thought about it. I am not sure I would ever use up the total number shown, but it can certainly be over several million of them over time.
– Moo
Dec 13 '18 at 17:22
|
show 2 more comments
RandomSample[
Union[CharacterRange["a", "z"], CharacterRange["0", "9"]], 6]
or
RandomSample[Flatten[CharacterRange @@@ {{"a", "z"}, {"0", "9"}}], 6]
or
RandomSample[Join @@ (CharacterRange @@@ {{"a", "z"}, {"0", "9"}}), 6]
This guarantees no collisions because RandomSample
selects elements without replacement.
How does does guarantee no collisions?
– Moo
Dec 13 '18 at 15:31
add a comment |
Inspired by some of the other answers and comments, here's a rather silly brute-force approach. We can RandomSample
a range that we can use to enumerate all combinations.
range = Range[0, 36^6 - 1];
(* This takes a little while: 15 seconds on my laptop. *)
chars = Union[CharacterRange["a", "z"], CharacterRange["0", "9"]];
makeString[n_] := ToString@Part[chars, 1 + IntegerDigits[n, 36, 6]];
Then
makeString /@ RandomSample[range, 1000]
will always return a bunch of unique strings.
2
This becomes much less silly if you useRandomSample[0 ;; 36^6 - 1, 1000]
instead. This way, the humongous listrange
need not be created and 1000 words are created within 4 ms. See also Carl's answer.
– Henrik Schumacher
Dec 13 '18 at 21:56
Holy cow I had no idea that worked!
– Pillsy
Dec 13 '18 at 23:34
add a comment |
Following is what you want. Unfortunately it takes time to generate all possible set for n=6
. But for n=5
it works. And it is guaranteed that there is no repeated element.
val = Tuples[Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 5];
RandomSample[val, 5]
Much smart way is
DeleteDuplicates[
Table[RandomSample[
Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 6], 5]]
It is very unlikely to generate the same element.
n = 10000;
Length@DeleteDuplicates[
Table[RandomSample[
Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 6], n]] ==
n
True
But when you increase n
Table[n = 100000;
n - Length@
DeleteDuplicates[
Table[RandomSample[
Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 6], n]],
10] // Max
5
This means 5 elements are repeated when we generate 100000 sample.. Of course, it might be larger than 5.
add a comment |
Your Answer
StackExchange.ifUsing("editor", function () {
return StackExchange.using("mathjaxEditing", function () {
StackExchange.MarkdownEditor.creationCallbacks.add(function (editor, postfix) {
StackExchange.mathjaxEditing.prepareWmdForMathJax(editor, postfix, [["$", "$"], ["\\(","\\)"]]);
});
});
}, "mathjax-editing");
StackExchange.ready(function() {
var channelOptions = {
tags: "".split(" "),
id: "387"
};
initTagRenderer("".split(" "), "".split(" "), channelOptions);
StackExchange.using("externalEditor", function() {
// Have to fire editor after snippets, if snippets enabled
if (StackExchange.settings.snippets.snippetsEnabled) {
StackExchange.using("snippets", function() {
createEditor();
});
}
else {
createEditor();
}
});
function createEditor() {
StackExchange.prepareEditor({
heartbeatType: 'answer',
autoActivateHeartbeat: false,
convertImagesToLinks: false,
noModals: true,
showLowRepImageUploadWarning: true,
reputationToPostImages: null,
bindNavPrevention: true,
postfix: "",
imageUploader: {
brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
allowUrls: true
},
onDemand: true,
discardSelector: ".discard-answer"
,immediatelyShowMarkdownHelp:true
});
}
});
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fmathematica.stackexchange.com%2fquestions%2f187829%2frandom-six-character-strings-without-collisions%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
4 Answers
4
active
oldest
votes
4 Answers
4
active
oldest
votes
active
oldest
votes
active
oldest
votes
Just changing RandomChoice
to RandomSample
doesn't help, since RandomSample
just means that none of the characters are repeated, and clearly you want to allow repeated characters, since one of your strings is "35UVUS". One idea is to oversample and remove duplicates. For example:
SeedRandom[1]
Take[
DeleteDuplicates[rndnew[{10, 6}]],
UpTo[5]
]
{"K1263G", "SXVXHC", "UO2PBL", "EC1FTJ", "0TKLEH"}
Another possibility is to index the possible random strings, and then do a random sample from the possible indices. For your case, the number of possible strings is simply 36^6. To convert from an index to a string:
characters = Join[CharacterRange["A","Z"], CharacterRange["0","9"]];
fromIndex[index_, len_] := StringJoin[
characters[[1+IntegerDigits[index, 36, len]]]
]
Then, a function that returns n
samples of length len
strings:
sample[n_, len_] := fromIndex[#, len]& /@ RandomSample[1 ;; 36^len, n]
Example:
SeedRandom[1]
sample[5, 6]
{"0621O7", "0WH6XW", "ODLV4Z", "KWSN6U", "AMOSFA"}
Is there a way to generate some number of these, keep the state of the RNG and use it to reseed from that point moving forward so we can maintain uniqueness of all six-characters over time?
– Moo
Dec 13 '18 at 16:18
@Moo Not that I'm aware of. Do you know how many unique strings you want in total?
– Carl Woll
Dec 13 '18 at 16:49
If I am doing my math correctly, we have 6-character strings where strings can repeat, then there are $26$ letters plus $10$ digits in the pool of characters, giving us $36$ in all per character. This means we would have $36^6 = 2176782336$ combinations.
– Moo
Dec 13 '18 at 16:52
1
@Moo There are 36^6 total strings, but how many do you want to generate? There is no point in using a random approach if you want to generate all of them.
– Carl Woll
Dec 13 '18 at 17:04
CarlWoll: The issue is that I would generate something like $10000$ at a time, use them and then generate a new batch and over time, duplicates matter. Maybe there is a better way based on that, but I haven't thought about it. I am not sure I would ever use up the total number shown, but it can certainly be over several million of them over time.
– Moo
Dec 13 '18 at 17:22
|
show 2 more comments
Just changing RandomChoice
to RandomSample
doesn't help, since RandomSample
just means that none of the characters are repeated, and clearly you want to allow repeated characters, since one of your strings is "35UVUS". One idea is to oversample and remove duplicates. For example:
SeedRandom[1]
Take[
DeleteDuplicates[rndnew[{10, 6}]],
UpTo[5]
]
{"K1263G", "SXVXHC", "UO2PBL", "EC1FTJ", "0TKLEH"}
Another possibility is to index the possible random strings, and then do a random sample from the possible indices. For your case, the number of possible strings is simply 36^6. To convert from an index to a string:
characters = Join[CharacterRange["A","Z"], CharacterRange["0","9"]];
fromIndex[index_, len_] := StringJoin[
characters[[1+IntegerDigits[index, 36, len]]]
]
Then, a function that returns n
samples of length len
strings:
sample[n_, len_] := fromIndex[#, len]& /@ RandomSample[1 ;; 36^len, n]
Example:
SeedRandom[1]
sample[5, 6]
{"0621O7", "0WH6XW", "ODLV4Z", "KWSN6U", "AMOSFA"}
Is there a way to generate some number of these, keep the state of the RNG and use it to reseed from that point moving forward so we can maintain uniqueness of all six-characters over time?
– Moo
Dec 13 '18 at 16:18
@Moo Not that I'm aware of. Do you know how many unique strings you want in total?
– Carl Woll
Dec 13 '18 at 16:49
If I am doing my math correctly, we have 6-character strings where strings can repeat, then there are $26$ letters plus $10$ digits in the pool of characters, giving us $36$ in all per character. This means we would have $36^6 = 2176782336$ combinations.
– Moo
Dec 13 '18 at 16:52
1
@Moo There are 36^6 total strings, but how many do you want to generate? There is no point in using a random approach if you want to generate all of them.
– Carl Woll
Dec 13 '18 at 17:04
CarlWoll: The issue is that I would generate something like $10000$ at a time, use them and then generate a new batch and over time, duplicates matter. Maybe there is a better way based on that, but I haven't thought about it. I am not sure I would ever use up the total number shown, but it can certainly be over several million of them over time.
– Moo
Dec 13 '18 at 17:22
|
show 2 more comments
Just changing RandomChoice
to RandomSample
doesn't help, since RandomSample
just means that none of the characters are repeated, and clearly you want to allow repeated characters, since one of your strings is "35UVUS". One idea is to oversample and remove duplicates. For example:
SeedRandom[1]
Take[
DeleteDuplicates[rndnew[{10, 6}]],
UpTo[5]
]
{"K1263G", "SXVXHC", "UO2PBL", "EC1FTJ", "0TKLEH"}
Another possibility is to index the possible random strings, and then do a random sample from the possible indices. For your case, the number of possible strings is simply 36^6. To convert from an index to a string:
characters = Join[CharacterRange["A","Z"], CharacterRange["0","9"]];
fromIndex[index_, len_] := StringJoin[
characters[[1+IntegerDigits[index, 36, len]]]
]
Then, a function that returns n
samples of length len
strings:
sample[n_, len_] := fromIndex[#, len]& /@ RandomSample[1 ;; 36^len, n]
Example:
SeedRandom[1]
sample[5, 6]
{"0621O7", "0WH6XW", "ODLV4Z", "KWSN6U", "AMOSFA"}
Just changing RandomChoice
to RandomSample
doesn't help, since RandomSample
just means that none of the characters are repeated, and clearly you want to allow repeated characters, since one of your strings is "35UVUS". One idea is to oversample and remove duplicates. For example:
SeedRandom[1]
Take[
DeleteDuplicates[rndnew[{10, 6}]],
UpTo[5]
]
{"K1263G", "SXVXHC", "UO2PBL", "EC1FTJ", "0TKLEH"}
Another possibility is to index the possible random strings, and then do a random sample from the possible indices. For your case, the number of possible strings is simply 36^6. To convert from an index to a string:
characters = Join[CharacterRange["A","Z"], CharacterRange["0","9"]];
fromIndex[index_, len_] := StringJoin[
characters[[1+IntegerDigits[index, 36, len]]]
]
Then, a function that returns n
samples of length len
strings:
sample[n_, len_] := fromIndex[#, len]& /@ RandomSample[1 ;; 36^len, n]
Example:
SeedRandom[1]
sample[5, 6]
{"0621O7", "0WH6XW", "ODLV4Z", "KWSN6U", "AMOSFA"}
edited Dec 13 '18 at 16:47
answered Dec 13 '18 at 16:15
Carl Woll
67.1k388175
67.1k388175
Is there a way to generate some number of these, keep the state of the RNG and use it to reseed from that point moving forward so we can maintain uniqueness of all six-characters over time?
– Moo
Dec 13 '18 at 16:18
@Moo Not that I'm aware of. Do you know how many unique strings you want in total?
– Carl Woll
Dec 13 '18 at 16:49
If I am doing my math correctly, we have 6-character strings where strings can repeat, then there are $26$ letters plus $10$ digits in the pool of characters, giving us $36$ in all per character. This means we would have $36^6 = 2176782336$ combinations.
– Moo
Dec 13 '18 at 16:52
1
@Moo There are 36^6 total strings, but how many do you want to generate? There is no point in using a random approach if you want to generate all of them.
– Carl Woll
Dec 13 '18 at 17:04
CarlWoll: The issue is that I would generate something like $10000$ at a time, use them and then generate a new batch and over time, duplicates matter. Maybe there is a better way based on that, but I haven't thought about it. I am not sure I would ever use up the total number shown, but it can certainly be over several million of them over time.
– Moo
Dec 13 '18 at 17:22
|
show 2 more comments
Is there a way to generate some number of these, keep the state of the RNG and use it to reseed from that point moving forward so we can maintain uniqueness of all six-characters over time?
– Moo
Dec 13 '18 at 16:18
@Moo Not that I'm aware of. Do you know how many unique strings you want in total?
– Carl Woll
Dec 13 '18 at 16:49
If I am doing my math correctly, we have 6-character strings where strings can repeat, then there are $26$ letters plus $10$ digits in the pool of characters, giving us $36$ in all per character. This means we would have $36^6 = 2176782336$ combinations.
– Moo
Dec 13 '18 at 16:52
1
@Moo There are 36^6 total strings, but how many do you want to generate? There is no point in using a random approach if you want to generate all of them.
– Carl Woll
Dec 13 '18 at 17:04
CarlWoll: The issue is that I would generate something like $10000$ at a time, use them and then generate a new batch and over time, duplicates matter. Maybe there is a better way based on that, but I haven't thought about it. I am not sure I would ever use up the total number shown, but it can certainly be over several million of them over time.
– Moo
Dec 13 '18 at 17:22
Is there a way to generate some number of these, keep the state of the RNG and use it to reseed from that point moving forward so we can maintain uniqueness of all six-characters over time?
– Moo
Dec 13 '18 at 16:18
Is there a way to generate some number of these, keep the state of the RNG and use it to reseed from that point moving forward so we can maintain uniqueness of all six-characters over time?
– Moo
Dec 13 '18 at 16:18
@Moo Not that I'm aware of. Do you know how many unique strings you want in total?
– Carl Woll
Dec 13 '18 at 16:49
@Moo Not that I'm aware of. Do you know how many unique strings you want in total?
– Carl Woll
Dec 13 '18 at 16:49
If I am doing my math correctly, we have 6-character strings where strings can repeat, then there are $26$ letters plus $10$ digits in the pool of characters, giving us $36$ in all per character. This means we would have $36^6 = 2176782336$ combinations.
– Moo
Dec 13 '18 at 16:52
If I am doing my math correctly, we have 6-character strings where strings can repeat, then there are $26$ letters plus $10$ digits in the pool of characters, giving us $36$ in all per character. This means we would have $36^6 = 2176782336$ combinations.
– Moo
Dec 13 '18 at 16:52
1
1
@Moo There are 36^6 total strings, but how many do you want to generate? There is no point in using a random approach if you want to generate all of them.
– Carl Woll
Dec 13 '18 at 17:04
@Moo There are 36^6 total strings, but how many do you want to generate? There is no point in using a random approach if you want to generate all of them.
– Carl Woll
Dec 13 '18 at 17:04
CarlWoll: The issue is that I would generate something like $10000$ at a time, use them and then generate a new batch and over time, duplicates matter. Maybe there is a better way based on that, but I haven't thought about it. I am not sure I would ever use up the total number shown, but it can certainly be over several million of them over time.
– Moo
Dec 13 '18 at 17:22
CarlWoll: The issue is that I would generate something like $10000$ at a time, use them and then generate a new batch and over time, duplicates matter. Maybe there is a better way based on that, but I haven't thought about it. I am not sure I would ever use up the total number shown, but it can certainly be over several million of them over time.
– Moo
Dec 13 '18 at 17:22
|
show 2 more comments
RandomSample[
Union[CharacterRange["a", "z"], CharacterRange["0", "9"]], 6]
or
RandomSample[Flatten[CharacterRange @@@ {{"a", "z"}, {"0", "9"}}], 6]
or
RandomSample[Join @@ (CharacterRange @@@ {{"a", "z"}, {"0", "9"}}), 6]
This guarantees no collisions because RandomSample
selects elements without replacement.
How does does guarantee no collisions?
– Moo
Dec 13 '18 at 15:31
add a comment |
RandomSample[
Union[CharacterRange["a", "z"], CharacterRange["0", "9"]], 6]
or
RandomSample[Flatten[CharacterRange @@@ {{"a", "z"}, {"0", "9"}}], 6]
or
RandomSample[Join @@ (CharacterRange @@@ {{"a", "z"}, {"0", "9"}}), 6]
This guarantees no collisions because RandomSample
selects elements without replacement.
How does does guarantee no collisions?
– Moo
Dec 13 '18 at 15:31
add a comment |
RandomSample[
Union[CharacterRange["a", "z"], CharacterRange["0", "9"]], 6]
or
RandomSample[Flatten[CharacterRange @@@ {{"a", "z"}, {"0", "9"}}], 6]
or
RandomSample[Join @@ (CharacterRange @@@ {{"a", "z"}, {"0", "9"}}), 6]
This guarantees no collisions because RandomSample
selects elements without replacement.
RandomSample[
Union[CharacterRange["a", "z"], CharacterRange["0", "9"]], 6]
or
RandomSample[Flatten[CharacterRange @@@ {{"a", "z"}, {"0", "9"}}], 6]
or
RandomSample[Join @@ (CharacterRange @@@ {{"a", "z"}, {"0", "9"}}), 6]
This guarantees no collisions because RandomSample
selects elements without replacement.
edited Dec 13 '18 at 15:44
answered Dec 13 '18 at 15:29
David G. Stork
23.3k22051
23.3k22051
How does does guarantee no collisions?
– Moo
Dec 13 '18 at 15:31
add a comment |
How does does guarantee no collisions?
– Moo
Dec 13 '18 at 15:31
How does does guarantee no collisions?
– Moo
Dec 13 '18 at 15:31
How does does guarantee no collisions?
– Moo
Dec 13 '18 at 15:31
add a comment |
Inspired by some of the other answers and comments, here's a rather silly brute-force approach. We can RandomSample
a range that we can use to enumerate all combinations.
range = Range[0, 36^6 - 1];
(* This takes a little while: 15 seconds on my laptop. *)
chars = Union[CharacterRange["a", "z"], CharacterRange["0", "9"]];
makeString[n_] := ToString@Part[chars, 1 + IntegerDigits[n, 36, 6]];
Then
makeString /@ RandomSample[range, 1000]
will always return a bunch of unique strings.
2
This becomes much less silly if you useRandomSample[0 ;; 36^6 - 1, 1000]
instead. This way, the humongous listrange
need not be created and 1000 words are created within 4 ms. See also Carl's answer.
– Henrik Schumacher
Dec 13 '18 at 21:56
Holy cow I had no idea that worked!
– Pillsy
Dec 13 '18 at 23:34
add a comment |
Inspired by some of the other answers and comments, here's a rather silly brute-force approach. We can RandomSample
a range that we can use to enumerate all combinations.
range = Range[0, 36^6 - 1];
(* This takes a little while: 15 seconds on my laptop. *)
chars = Union[CharacterRange["a", "z"], CharacterRange["0", "9"]];
makeString[n_] := ToString@Part[chars, 1 + IntegerDigits[n, 36, 6]];
Then
makeString /@ RandomSample[range, 1000]
will always return a bunch of unique strings.
2
This becomes much less silly if you useRandomSample[0 ;; 36^6 - 1, 1000]
instead. This way, the humongous listrange
need not be created and 1000 words are created within 4 ms. See also Carl's answer.
– Henrik Schumacher
Dec 13 '18 at 21:56
Holy cow I had no idea that worked!
– Pillsy
Dec 13 '18 at 23:34
add a comment |
Inspired by some of the other answers and comments, here's a rather silly brute-force approach. We can RandomSample
a range that we can use to enumerate all combinations.
range = Range[0, 36^6 - 1];
(* This takes a little while: 15 seconds on my laptop. *)
chars = Union[CharacterRange["a", "z"], CharacterRange["0", "9"]];
makeString[n_] := ToString@Part[chars, 1 + IntegerDigits[n, 36, 6]];
Then
makeString /@ RandomSample[range, 1000]
will always return a bunch of unique strings.
Inspired by some of the other answers and comments, here's a rather silly brute-force approach. We can RandomSample
a range that we can use to enumerate all combinations.
range = Range[0, 36^6 - 1];
(* This takes a little while: 15 seconds on my laptop. *)
chars = Union[CharacterRange["a", "z"], CharacterRange["0", "9"]];
makeString[n_] := ToString@Part[chars, 1 + IntegerDigits[n, 36, 6]];
Then
makeString /@ RandomSample[range, 1000]
will always return a bunch of unique strings.
answered Dec 13 '18 at 17:17
Pillsy
12.7k13179
12.7k13179
2
This becomes much less silly if you useRandomSample[0 ;; 36^6 - 1, 1000]
instead. This way, the humongous listrange
need not be created and 1000 words are created within 4 ms. See also Carl's answer.
– Henrik Schumacher
Dec 13 '18 at 21:56
Holy cow I had no idea that worked!
– Pillsy
Dec 13 '18 at 23:34
add a comment |
2
This becomes much less silly if you useRandomSample[0 ;; 36^6 - 1, 1000]
instead. This way, the humongous listrange
need not be created and 1000 words are created within 4 ms. See also Carl's answer.
– Henrik Schumacher
Dec 13 '18 at 21:56
Holy cow I had no idea that worked!
– Pillsy
Dec 13 '18 at 23:34
2
2
This becomes much less silly if you use
RandomSample[0 ;; 36^6 - 1, 1000]
instead. This way, the humongous list range
need not be created and 1000 words are created within 4 ms. See also Carl's answer.– Henrik Schumacher
Dec 13 '18 at 21:56
This becomes much less silly if you use
RandomSample[0 ;; 36^6 - 1, 1000]
instead. This way, the humongous list range
need not be created and 1000 words are created within 4 ms. See also Carl's answer.– Henrik Schumacher
Dec 13 '18 at 21:56
Holy cow I had no idea that worked!
– Pillsy
Dec 13 '18 at 23:34
Holy cow I had no idea that worked!
– Pillsy
Dec 13 '18 at 23:34
add a comment |
Following is what you want. Unfortunately it takes time to generate all possible set for n=6
. But for n=5
it works. And it is guaranteed that there is no repeated element.
val = Tuples[Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 5];
RandomSample[val, 5]
Much smart way is
DeleteDuplicates[
Table[RandomSample[
Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 6], 5]]
It is very unlikely to generate the same element.
n = 10000;
Length@DeleteDuplicates[
Table[RandomSample[
Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 6], n]] ==
n
True
But when you increase n
Table[n = 100000;
n - Length@
DeleteDuplicates[
Table[RandomSample[
Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 6], n]],
10] // Max
5
This means 5 elements are repeated when we generate 100000 sample.. Of course, it might be larger than 5.
add a comment |
Following is what you want. Unfortunately it takes time to generate all possible set for n=6
. But for n=5
it works. And it is guaranteed that there is no repeated element.
val = Tuples[Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 5];
RandomSample[val, 5]
Much smart way is
DeleteDuplicates[
Table[RandomSample[
Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 6], 5]]
It is very unlikely to generate the same element.
n = 10000;
Length@DeleteDuplicates[
Table[RandomSample[
Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 6], n]] ==
n
True
But when you increase n
Table[n = 100000;
n - Length@
DeleteDuplicates[
Table[RandomSample[
Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 6], n]],
10] // Max
5
This means 5 elements are repeated when we generate 100000 sample.. Of course, it might be larger than 5.
add a comment |
Following is what you want. Unfortunately it takes time to generate all possible set for n=6
. But for n=5
it works. And it is guaranteed that there is no repeated element.
val = Tuples[Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 5];
RandomSample[val, 5]
Much smart way is
DeleteDuplicates[
Table[RandomSample[
Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 6], 5]]
It is very unlikely to generate the same element.
n = 10000;
Length@DeleteDuplicates[
Table[RandomSample[
Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 6], n]] ==
n
True
But when you increase n
Table[n = 100000;
n - Length@
DeleteDuplicates[
Table[RandomSample[
Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 6], n]],
10] // Max
5
This means 5 elements are repeated when we generate 100000 sample.. Of course, it might be larger than 5.
Following is what you want. Unfortunately it takes time to generate all possible set for n=6
. But for n=5
it works. And it is guaranteed that there is no repeated element.
val = Tuples[Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 5];
RandomSample[val, 5]
Much smart way is
DeleteDuplicates[
Table[RandomSample[
Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 6], 5]]
It is very unlikely to generate the same element.
n = 10000;
Length@DeleteDuplicates[
Table[RandomSample[
Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 6], n]] ==
n
True
But when you increase n
Table[n = 100000;
n - Length@
DeleteDuplicates[
Table[RandomSample[
Join @@ (CharacterRange @@@ {{"A", "Z"}, {"0", "9"}}), 6], n]],
10] // Max
5
This means 5 elements are repeated when we generate 100000 sample.. Of course, it might be larger than 5.
edited Dec 13 '18 at 18:50
answered Dec 13 '18 at 17:22
Okkes Dulgerci
4,0851816
4,0851816
add a comment |
add a comment |
Thanks for contributing an answer to Mathematica Stack Exchange!
- Please be sure to answer the question. Provide details and share your research!
But avoid …
- Asking for help, clarification, or responding to other answers.
- Making statements based on opinion; back them up with references or personal experience.
Use MathJax to format equations. MathJax reference.
To learn more, see our tips on writing great answers.
Some of your past answers have not been well-received, and you're in danger of being blocked from answering.
Please pay close attention to the following guidance:
- Please be sure to answer the question. Provide details and share your research!
But avoid …
- Asking for help, clarification, or responding to other answers.
- Making statements based on opinion; back them up with references or personal experience.
To learn more, see our tips on writing great answers.
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fmathematica.stackexchange.com%2fquestions%2f187829%2frandom-six-character-strings-without-collisions%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
5
replace
RandomChoice
withRandomSample
?– kglr
Dec 13 '18 at 14:20
@kglr: I will certainly look into that. Thanks for the pointer!
– Moo
Dec 13 '18 at 14:21
2
When a function is close to what you want, look at the
See Also
section of that function's documentation.– Bob Hanlon
Dec 13 '18 at 14:39
Sorry that I'm not a Mathematica user, so just provide my thought on solving this in pseudo code: while less than 5 strings in the collection: generate a random string if new string already exists in the collection: do nothing else: add it to the collection No collisions guaranteed, but might take a while.
– Kyle R.
Dec 14 '18 at 0:41