C 如何在没有rand()函数的情况下生成随机数?

C 如何在没有rand()函数的情况下生成随机数?,c,random,C,Random,我想生成0到某个整数之间的(伪)随机数。我不介意它们是否太随机。我可以访问一天中的当前时间,但不能访问rand功能。有人能想出一个足够强大的方法来生成这些吗?也许,从一天中的某个时间丢弃一些位,然后取整数的模或其他什么 我正在使用c。看看如何实现一个你自己的伪随机数生成器(例如,rand()),它受到高度重视。唯一“健壮”(不容易预测)的方法是编写你自己的伪随机数生成器,并用当前时间进行播种。强制性维基百科链接:您可以在这里获得“微小的梅森龙卷风”: 它是纯c语言,使用简单。例如,仅利用时间:

我想生成0到某个整数之间的(伪)随机数。我不介意它们是否太随机。我可以访问一天中的当前时间,但不能访问rand功能。有人能想出一个足够强大的方法来生成这些吗?也许,从一天中的某个时间丢弃一些位,然后取整数的模或其他什么


我正在使用c。

看看如何实现一个你自己的伪随机数生成器(例如,
rand()
),它受到高度重视。

唯一“健壮”(不容易预测)的方法是编写你自己的伪随机数生成器,并用当前时间进行播种。强制性维基百科链接:

您可以在这里获得“微小的梅森龙卷风”:

它是纯c语言,使用简单。例如,仅利用时间:

#include "tinymt32.h"
// And if you can't link:
#include "tinymt32.c"

#include <time.h>
#include <stdio.h>

int main(int argc, const char* argv[])
{
    tinymt32_t state;
    uint32_t seed = time(0);

    tinymt32_init(&state, seed);

    for (int i=0; i<10; i++)
            printf("random number %d: %u\n", i, (unsigned int)tinymt32_generate_uint32(&state));
}
#包括“tinymt32.h”
//如果您无法链接:
#包括“tinymt32.c”
#包括
#包括
int main(int argc,const char*argv[]
{
tinymt32_t状态;
uint32_t seed=时间(0);
tinymt32_初始(&状态,种子);

对于(inti=0;i来说,如果您正在寻找一个超简单的伪随机生成器,您可以使用一个

wikipedia文章中有一些代码片段供您查看,但基本上16位生成器的代码看起来是这样的(从该页面轻轻按摩…)

无符号短lfsr=0xACE1u;
无符号位;
无符号兰德()
{
位=((lfsr>>0)^(lfsr>>2)^(lfsr>>3)^(lfsr>>5))&1;
返回lfsr=(lfsr>>1)|(位对于“不太随机”的整数,您可以从当前UNIX时间开始,然后使用递归公式
r=((r*7621)+1)%32768;
0
(包括)和
M
(排除)之间的第n个随机整数在第n次迭代后将是
r%M

这称为线性同余生成器

递归公式是bzip2在其快速排序实现中用于选择枢轴的公式。我不知道还有其他用途,但它在这一特定用途中非常有效…

#include
#include<stdio.h>
#include<conio.h>
#include<stdlib.h>
int main()
{
unsigned int x,r,i;
// no of random no you want to generate
scanf("%d",&x);
// put the range of random no 
scanf("%d",&r);
unsigned int *a=(unsigned int*)malloc(sizeof(unsigned int)*x);
for(i=0;i<x;i++)
printf("%d ",(a[i]%r)+1);   
free(a);
getch();
return 0;
}
#包括 #包括 int main() { 无符号整数x,r,i; //要生成的随机编号的编号 scanf(“%d”和&x); //把随机数的范围设为否 scanf(“%d”、&r); 无符号整数*a=(无符号整数*)malloc(sizeof(无符号整数)*x);
对于(i=0;i一个最简单的随机数生成器,它不返回所有相同的值:

uint16_t simpleRand(void)
  {
    static uint16_t r = 5531; //dont realy care about start value
    r+=941; //this value must be relative prime to 2^16, so we use all values
    return r;
  }  

如果您不希望序列总是以相同的值开始,您可以获得设置开始值的时间。

下面提供了一个最小且简单的随机生成器,它可以在范围内工作

unsigned int MyRand(unsigned int start_range,unsigned int end_range)
  {
    static unsigned int rand = 0xACE1U; /* Any nonzero start state will work. */

    /*check for valid range.*/
    if(start_range == end_range) {
        return start_range;
    }

    /*get the random in end-range.*/
    rand += 0x3AD;
    rand %= end_range;

    /*get the random in start-range.*/
    while(rand < start_range){
        rand = rand + end_range - start_range;
    }

    return rand;
  }

int main(void)
{
    int i;
    for (i = 0; i < 0xFF; i++)
    {
    printf("%u\t",MyRand(10,20));
    }
    return 0;
}
unsigned int MyRand(unsigned int start\u范围,unsigned int end\u范围)
{
静态unsigned int rand=0xACE1U;/*任何非零启动状态都可以工作*/
/*检查有效范围*/
如果(开始范围==结束范围){
返回起始范围;
}
/*获取末端范围内的随机值*/
rand+=0x3AD;
rand%=结束时间范围;
/*获取起始范围内的随机值*/
while(rand
如果您生成数字的速度不太快(*1),并且上限足够低(*2),并且您的“一天中的时间”包括纳秒,请使用这些纳秒

#include <stdio.h>
#include <stdlib.h>
#include <time.h>

int nanorand(void) {
    struct timespec p[1];
    clock_gettime(CLOCK_MONOTONIC, p);
    return p->tv_nsec % 1000;
}

int main(void) {
    int r, x;
    for (;;) {
        r = nanorand();
        do {
            printf("please type %d (< 50 quits): ", r);
            fflush(stdout);
            if (scanf("%d", &x) != 1) exit(EXIT_FAILURE);
        } while (x != r);
        if (r < 50) break;
    }
    puts("");
    return 0;
}
#包括
#包括
#包括
国际纳米级(无效){
结构timespec p[1];
时钟获取时间(时钟单调,p);
返回p->tv\u nsec%1000;
}
内部主(空){
int r,x;
对于(;;){
r=nanorand();
做{
printf(“请键入%d(<50退出):”,r);
fflush(stdout);
如果(scanf(“%d”,&x)!=1)退出(退出失败);
}而(x!=r);
如果(r<50)断裂;
}
认沽权(“”);
返回0;
}
和一个样本运行

please type 769 (< 50 quits): 769 please type 185 (< 50 quits): 185 please type 44 (< 50 quits): 44 请键入769(<50退出):769 请键入185(<50退出):185 请键入44(<50退出):44 (*1)如果您以交互方式使用它们,请一次使用一个
(*2)如果您希望数字达到1000左右,请导入java.io.*; 公共类随机{ 公共静态类p{ } 静态长reg=0; 静态长lfsr() { 如果(reg==0) { reg=145896027340307l; } 长位=(reg>>0^reg>>2^reg>>3^reg>>5)&1; reg=reg>>1位
#包含
整数取整数(整数低,整数高){
自动时刻=标准::计时::稳定的时钟::现在().自纪元以来的时间().计数();
int num=力矩%(高-低+1);
返回num+lo;
}
#包括
int main(){
int-num;
时间秒;
秒=时间(空);
printf(“输入随机数的范围:\n”);
scanf(“%d”和&num);
如果(数值>0)
{
对于(;;)
{
秒=秒%3600;
如果(数值>=秒)
{
printf(“%ld\n”,秒);
打破
}
秒=秒%num;
}
}
其他的
{
printf(“请输入正值!\n”);
}
返回0;
}

这听起来像是家庭作业。如果是的话,你应该用“家庭作业”标记。如果你可以访问google.com,试着搜索这个:“随机数生成器”。为什么不直接从
/dev/random
?或者使用xkcd方法。是什么阻止你简单地使用
random()
然后?rand()通常实现非常简单(使用简单的种子乘法,然后混合)…通常只有一行。只需谷歌一下。我不能使用任何其他库!不能是什么意思?包括另一个#include“tinymt32.c”怎么样?正是我所需要的!一个非常简单和优雅的解决方案这很有效。当你需要一个不同的数字流时,只需要更改lfsr。你能为你的代码提供一个解释吗?请阅读请停止使用不推荐的头文件。你至少应该应用一些适当的缩进。添加一个解释会很有用w您的实现是为了工作。而且
sec=sec%3600;
是错误的。为什么要使用循环?范围是appli please type 769 (< 50 quits): 769 please type 185 (< 50 quits): 185 please type 44 (< 50 quits): 44
import java.io.*;
public class random{
public static class p{

}
static long reg=0;
static long lfsr()
{
    if(reg==0)
    {
        reg=145896027340307l;
    }
    long bit=(reg>>0^reg>>2^reg>>3^reg>>5)&1;
    reg=reg>>1|bit<<62;
    return reg;
}
static long getRand()
{
    String s=String.valueOf(new p());
    //System.out.println(s);
    long n=0;
    lfsr();
    for(int i=0;i<s.length();i++)
    {
        n=n<<8|+s.charAt(i);
    }
    System.out.print(n+" "+System.currentTimeMillis()+" "+reg+" ");
    n=n^System.currentTimeMillis()^reg;
    return n;
}
public static void main(String args[])throws IOException
{
    for(int i=0;i<400;i++)
    {
        System.out.println(getRand());
    }
}
#include <chrono>

int get_rand(int lo, int hi) {
    auto moment = std::chrono::steady_clock::now().time_since_epoch().count();
    int num = moment % (hi - lo + 1);
    return num + lo;
}
#include<time.h>
int main(){
int num;
time_t sec;
sec=time(NULL);
printf("Enter the Range under which you want Random number:\n");
scanf("%d",&num);
if(num>0)
{
for(;;)
{
sec=sec%3600;
if(num>=sec)
{
printf("%ld\n",sec);
break;
}
sec=sec%num;
}
}
else
{
printf("Please Enter Positive Value!\n");
}
return 0;
}