在給定範圍中取不重複的隨機數

2021-10-02 04:35:56 字數 1973 閱讀 5267

在給定範圍中取不重複的隨機數

隨機取m個數(在1到n的範圍之內),(m<=n),要求m個數沒有重複。有沒有什麼好的演算法,時間複雜度和空間複雜度都很好?

方法一:用stl中的set集,紅黑樹來處理

取隨機數可以用c++標準的rand,至於m個不重複,用std::set來解決,把取到的隨機數插入到set裡面,通過set的size()==m來判斷是否已取夠m個了。

#include 

#include 

int main()

std::sets;

while(1)

int r = rand()%n;

s.insert(r);

if(s.size() == m)

break;

}//if

}//while

由於set底層實現是紅黑樹,插入複雜度是對數級。

方法二:

#include 

#include //用於rand()和srand()函式

#include //設定不同的隨機數

using namespace std;

int main (){

srand( time( 0 ) );    //呼叫不重複的隨機數函式

unsigned i;

for ( int n = 0; n++ < 10; )

i = rand() ;        //對i 賦系統的隨機數

cout << " the no." << n << "is : " << i << endl;

return 0;

1、 c++標準函式庫提供一隨機數生成器rand,返回0~rand_max之間均勻分布的偽隨機整數。 rand_max必須至少為32767。rand()函式不接受引數,預設以1為種子(即起始值)。隨機數生成器總是以相同的種子開始,所以形成的偽隨機數列也相同。失去了隨機意義。

2、c++中另一函式srand(),可以指定不同的數(無符號整數變元)為種子。但是如果種子相同,偽隨機數列也相同。

3、比較理想的是用變化的數,比如時間來作為隨機數生成器的種子。

在標頭檔案ctime中時間庫包含time函式,它可以返回乙個表示時間、日期、月和年的數值使用如下呼叫可將該值設為rand的種子

srand(static_cast(time(static_cast(null))));

4. 但srand()並不是說使隨機數都不一樣,它只是使取隨機數的種子隨著時間而改變。

方法三:以下方法需要附加空間b陣列,我們還是假設100個資料。

(1)將範圍陣列b[100](b[i]=100+i,不妨設陣列下標從1開始)的每個元素設定乙個標誌位flag,初始均為flag=0;若某元素被選入到a陣列中,則flag=1;顯然,以後再選到重複元素可以立刻判定是否已選。但是仍然有乙個很嚴重的問題,在小規模輸入下,無疑它的表現是不錯的。但現在舉乙個失敗的例子.

在1~65536之間,選擇65500個不重複的隨機數,看看後面的隨機數,比如第65500個數(最後乙個),它要在剩下的36個數中選擇才會有flag=0(根本不知道這36個數是什麼)。

改進:先在1~65536之間隨機選取36個數,刪除.將剩下的65500個數依次賦值給a[65500],然後打亂順序即可。

當範圍陣列與目標陣列的大小非常接近時,上述演算法非常有效,建議採用。

(2)問題的最終解決.

仍以最開始的那個例子來說,初始陣列b[i]=100+i,a陣列空。(a是我們需要的存放生成的隨即數的陣列,我們需要從b陣列中取數)

每次隨機生成陣列b的乙個下標subscript,然後取出它所對應的資料b[subscript],記下來給a當前的儲存單位a[j]。然後將陣列b的最後乙個數b[length]覆蓋b[subscript]的位置,同時將陣列a指向下乙個數,b陣列的長度減1。儘管前若干次生成的下標subscript隨機數有可能相同,但因為每一次都把最後乙個數填到取出的位置,因此,相同下標subscript對應的數卻絕不會相同,每一次取出的數都不會一樣,這樣,就保證了演算法的確定性、有效性、有窮性。

參考:

在給定範圍中取不重複的隨機數

在給定範圍中取不重複的隨機數 隨機取m 個數 在1到 n的範圍之內 m n 要求m 個數沒有重複。有沒有什麼好的演算法,時間複雜度和空間複雜度都很好?方法一 用 stl中的 set集,紅黑樹來處理 取隨機數可以用c 標準的rand 至於m 個不重複,用 std set 來解決,把取 到的隨機數插入到...

Lua在給定範圍內,生成指定個數不重複隨機數組

生成隨機數組,暫時發現兩種方法 1 把生成的數放到乙個表裡面,每次隨機時判斷這個表裡是否有,若有再隨機一次 問了朋友,很多人都想到這個方法 2 先生成乙個連續的數字表t,每次隨機乙個數n,把t n 儲存,並移除t n 首先,說一下我的真實需求是給定一定範圍,然後生成指定個數的不重複隨機數組。這個給定...

不重複隨機數

1 不重複隨機數1 生產 lowerbound,upperbound 的隨機數,核心 int upperbound lowerbound 1 rnd lowerbound 示例 如下 sub rndnumnorepeat1 dimdic dim i set dic createobject scri...