我正在試圖找到一個隨機數字,其中有1到max
數字(max
< 10)。找到一個隨機數字長度1到10,使用數字0到9而不重複
srand((int) time(NULL));
answer = ((rand() % max) + 1);
BUT:
0,... 9只允許使用一次。
我發現,等待rand()
創造這樣一些偶然的時間太長,所以我假設必須有創建運行總計其中每一個數字加一個比較時間由路。
我正在試圖找到一個隨機數字,其中有1到max
數字(max
< 10)。找到一個隨機數字長度1到10,使用數字0到9而不重複
srand((int) time(NULL));
answer = ((rand() % max) + 1);
BUT:
0,... 9只允許使用一次。
我發現,等待rand()
創造這樣一些偶然的時間太長,所以我假設必須有創建運行總計其中每一個數字加一個比較時間由路。
您可以逐個生成每個數字。首先,獲得一個從0
到9
的隨機整數。舉例來說,如果你得到5
,然後從所有的數字數組中刪除:
0 1 2 3 4 6 7 8 9
下得到一個隨機整數0
到8
,如果你得到8
這一次,那麼第二個數字是9
。刪除它並重復獲取下一個數字。
如果你需要獲得8位數字,例如,你到底有隻有4位離開,例如:
3 4 6 9
然後得到0
到3
一個隨機整數。例如,如果您得到0
,則最後一位數字是3
,其餘的數字將被丟棄。
您可以建立一個功能:
char * randstr(int len)
{
srand(0); //seed the generator
char * str = malloc(len); //allocate exactly len bytes
int i, x; //define some loop variables
char used = 0; //used is to check if the number has already been taken
char num; //a temp value
for (i = 0; i < len; i++)
{ //this loop runs through each character in the string
used = 1;
while (used) //basically, if we already used it, find another
{
used = 0;
num = rand() % 10 + 48; //48 = '8' //returns 0-9
for (x = 0; x < i; x++)
{ //this loop checks to see if its already been used
if (str[x] == num) used = 1;
}
}
}
return str;
}
這將返回一個字符數組,而不是一個空值終止之一,但所有的數字都將在ASCII碼形式。對於空終止的字符串,只需修改它就像這樣:
char * randstr(int len)
{
srand(0);
char * str = malloc(len + 1);
int i, x;
char used = 0;
char num;
for (i = 0; i < len; i++)
{
used = 1;
while (used)
{
used = 0;
num = rand() % 10 + 48; //48 = '8'
for (x = 0; x < i; x++)
{
if (str[x] == num) used = 1;
}
}
}
str[len - 1] = 0;
return str;
}
希望這有助於。
編輯: 該函數的工作方式,它返回一個字符串的大小len,只使用數字1-9,沒有重複。
調用randstr(5)可以返回類似
12345
93751
73485
...
待辦事項,如果沒有更多的數字使用,該功能將只是坐在那裏循環。 評論在第一個功能
獲取隨機數字的數字其實很簡單。我們只是希望通過
rand() % 10 + 1;
//so lets assign that to an int and call our function
int num = rand() % 10 + 1;
char * str = randstr(num); //assume this is the null terminated one
printf("The number was %s\n", str);
1和10完成之間的隨機數可以使用10個數字陣列,每一次洗牌他們,並得到了N個第一位數。僞代碼:
void shuffle(char[] a) {
for(int i=0; i< 10; i++) {
pos = rand() % 10;
swap(a[i], a[pos]);
}
}
int main() {
char arr[] = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9'};
# it prints endlessly random numbers of random length
while (1) {
shuffle(arr);
int N = rand() % 10 + 1; # how many digits to generate
for (int i=0; i<N; i++) {
printf(arr[i]);
}
}
printf("\n");
}
以這種方式可能的問題是,當「0」中出現了第一位,轉向變得比它需要較少的數目。但是你可以通過修改'shuffle'在第一個位置添加避免'0'(例如,檢查第一個是否爲0,然後生成隨機pos = rand()%9 + 1,然後swap(a [0],a [ POS])或得到的數字,如果你需要它。
你的洗牌不統一。查看「Fisher-Yates shuffle」上的維基百科頁面。 –
我同意 - 改善洗牌功能。感謝您的鏈接 – VladimirM
如果您正在尋找n
數字從0吸引到9,沒有重複(你的問題是很難解釋),那麼以下就足夠了一個整數。
的想法是把所有的數字從0到9的一頂帽子,然後畫出來一個接一個。每個附加到你正在構建的隨機整數值。
這頂帽子是一個數組初始設置0到9.
要在帽子中有k
個元素時繪製數字,請計算[0..k-1]
範圍內的隨機索引j
,並從該數組中獲取該元素。然後將最後一個(k-1
th)元素向下複製到位置j
,「刪除」它。剩餘的未使用數字現在在[0..k-2]中,您可以重複此過程直到完成。
追加一個數字d爲整數值是相同的話說
val = 10 * val + d
把這些想法放在一起,你有以下。注意,這允許第一個位置爲0,所以當打印時沒有前導零時,結果可能實際上只有一個小於n的數字。
unsigned random_unrepeated_digits(int n) {
int i, digits[] = { 0,1,2,3,4,5,6,7,8,9 };
unsigned val = 0;
for (i = 0; i < n; i++) {
int k = 10 - i, j = rand() % k;
val = 10 * val + digits[j];
digits[j] = digits[k - 1];
}
return val;
}
我剛剛在我的答案中寫了幾乎相同的代碼。我upvoted,但你需要小心不要以0開始結果,當n是10時,你的unsigned可能會溢出。 –
@匿名謝謝。我知道這些事情。事實上,我說它首先允許0,他並不排除。他的問題是不準確的。如果他真的排除這些東西,我會解決它們。 – Gene
您可以隨機數字{0,1,2,...,9},注意不要把0,然後再從最初的數字的適當數量的建設數量。通過這樣做,而構建的結果,當您去,和停止洗牌,一旦你已經解決了第一ndig
數字,你最終得到這樣的代碼:
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
long long rand_digits(int ndig) {
int digits[10] = {9, 8, 7, 6, 5, 4, 3, 2, 1, 0};
long long res = 0;
for (int i = 0; i < ndig; i++) {
int r = i + rand() % (10 - i - (i == 0));
res = res * 10 + digits[r];
digits[r] = digits[i];
}
return res;
}
int main(int argc, char *argv[]) {
srand((unsigned)time(0));
for (int i = 0; i < 10; i++) {
printf("%-2d: %lld\n", i + 1, rand_digits(i + 1));
}
return 0;
}
爲什麼不只是隨機生成每個十個位數? – Dmitri
但是我如何確保排除前幾位數字,如彩票中的數字。 – Simona
你說「最大數字」,但在你的示例代碼中,你暗示答案必須是從1到最大。這是什麼?所有的數字都可以在0到9的範圍內?你想要你的結果作爲一個字符串或'unsigned'或別的東西嗎? – Gene