自分のセンスや笑いの好みに影響を受けた作品を教えて

C言語について質問させて頂きます。
私は今、0以上50万以下(上限は50万以上ならどんな値でもかまいません)の範囲でランダムに整数を得たいと考えております。
#include <stdlib.h>のint rand(void)は0以上の乱数を返してくれますが、返す値はintの範囲内(?)なので、要望に合っておりません。
そこで、long型のランダムな値を得たいと思っております。
一体、どのような関数またはアルゴリズムを使えば、望むように出来るのでしょうか?
是非、お教えください。

A 回答 (9件)

手抜きで考えるなら


ランタイムのrandが 0から32767までを返すなら
randを値を2つ取って一方は4ビットシフトして0x7fff0まで作ります
他方の下位4ビットとの合計をします
この値から 希望の50万での剰余を求めるとか

long myRand( long limit ) {
  long nRes[2];
  nRes[0] = rnad() << 4;
  nRes[1] = rand();
  nRes[0] |= nRes[1] & 0x0F;
  return nRes[0] % limit;
}
    • good
    • 0
この回答へのお礼

ビット演算を利用するという私にとっては予想外な発想でのアルゴリズムをどうも有り難うございます。いい事を学べました。
このアルゴリズムを使うと100万でも1000万でもいけそうですね。
是非、活用させていただきます。

お礼日時:2008/07/09 21:23

回答というより補足説明っぽいですが。



昨今のコンパイラではintとlongはたいてい一緒なので、No.1の回答ままでもご期待の動作は得られるかと思います。
が、int型の大きさはコンパイラ依存なのであまり望ましくないのも事実ですね。キャストをlongにしてしまえば確実になります。

なおrand()の返す最大値はlimits.hのRAND_MAXで規定されています。大抵はshort、もしくはunsigned shortの最大値になっているでしょう。
    • good
    • 0
この回答へのお礼

説明を有難うございます。
limits.hをまた調べてみます。

お礼日時:2008/07/11 22:40

#7です。

訂正

元の値 剰余
0 0
1 1
2 2
3 0
でした。
多くなるのは0の場合ですね。
    • good
    • 0
この回答へのお礼

丁寧な回答を有難うございます。
どの値が出る回数が最も多いかはあまり気にしておりませんが、頻度については確認しておこうと思います。

お礼日時:2008/07/10 21:45

>rand()+rand() で、0~2*RAND_MAXまでの値が得られると思います。


この方法だと、RAND_MAX+1の値が一番多く出ることになってしまいます。
サイコロを2つ振ったときの合計は7が一番多くなるのと一緒ですね。

>この値から 希望の50万での剰余を求めるとか
これも微妙に良くないです。

例えば、0~3までの乱数発生器があったとして、0~2までの乱数が欲しい時、3での剰余を使うと
元の値 剰余
0 0
1 1
2 2
3 1
となって、1が出る確率が多くなります。
どうせ手抜きでも、目的の値より大きな値がでたら、もう一回やりなおしのほうがいいかと思います。
    • good
    • 0

それなりにまともな質の乱数が欲しいのなら、調べれば乱数アルゴリズムはみつかりますから、それに基づいて独自に実装するのがいいと思います。



乱数の質にこだわらないのなら、rand()を2回使えばいいと思います。
    • good
    • 0

rand()+rand() で、0~2*RAND_MAXまでの値が得られると思います。

    • good
    • 0
この回答へのお礼

小技なアイデアをどうも有り難うございます。
その作戦に気づきませんでした。
早速longの範囲でのランダム値が得られるようにやってみます。

お礼日時:2008/07/09 21:16

random() とか使えれば、それを利用するのがよい。

精度的な意味でも。
    • good
    • 0

まじめにいくならどこかから Mersenne Twister でもひろってくる.

    • good
    • 0

0~n の乱数


(int)((n + 1) * (rand() / (RAND_MAX + 1.0))
    • good
    • 0
この回答へのお礼

int型では希望の範囲の値が得られないんですけど、、
回答は有難うございます。

お礼日時:2008/07/09 21:25

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!


おすすめ情報