//包含头文件 void main() { int count=0; srand((unsigned)time(NULL)); for (int i=0;i <10;i++){ count++; cout <<"No"<<count<<"="<<rand()<<" "; if (!(count%5)) cout <<endl; } } |
No1=9694 No2=9694 No3=9694 No4=9694 No5=9694 No6=9694 No7=9694 No8=9694 No9=9694 No10=9694 |
No1=10351 No2=444 No3=11351 No4=3074 No5=21497 No6=30426 No7=6246 No8=24614 No9=22089 No10=21498 |
可以发现,以上两个程序段由于随机数生成时选择的种子的不同,运行的结果也不一样。rand()函数返回随机数序列中的下一个数(实际上是一个伪随机数序列,序列中的每一个数是由对其前面的数字进行复杂变换得到的)。为了模仿真正的随机性,首先要调用srand()函数给序列设置一个种子。为了更好地满足随机性,使用了时间函数time(),以便取到一个随时间变化的值,使每次运行rand()函数时从srand()函数所得到的种子值不相同。伪随机数生成器将作为"种子"的数当作初始整数传给函数。这粒种子会使这个球(生成伪随机数)一直滚下去。
程序段1中由于将srand()函数放在循环体内,而程序执行的CPU时间较快,调用time函数获取的时间精度却较低(55ms),这样循环体内每次产生随机数用到的种子数都是一样的,因此产生的随机数也是一样的。而程序段2中第1次产生的随机数要用到随机种子,以后的每次产生随机数都是利用递推关系得到的。
基于MFC的随机校验码生成
Web应用程序中经常要利用到随机校验码,校验码的主要作用是防止黑客利用工具软件在线破译用户登录密码,校验码、用户名、密码三者配合组成了进入Web应用系统的钥匙。在利用VC开发的基于客户机/浏览器(Client/Server)模式的应用软件系统中,为了防止非法用户入侵系统,通常也要运用随机校验码生成技术。
本实现要用到以上介绍到的伪随机数生成技术。校验码数据将以16进制码方式显示。主要代码如下:
void CRandompasswordDlg::OnCreatekey() { int RanCheckNum = 0; char out[25]={0}; char keytemp={0}; memset(out,0x30,18); srand((unsigned)timeGetTime());//产生随机数种子 for(int i=0;i <6;i++){ RanCheckNum = rand();//产生随机数 _itoa(RanCheckNum,keytemp,16);//将随机数转换成16进制 memcpy( &out[i*4],keytemp,strlen(keytemp)); } out[24]=0x00; strcpy(m_key.GetBuffer(18),out); UpdateData(FALSE); } |
图1 利用伪随机数生成随机校验码 |
图2 ImagePassword运行界面 |
图3 ImagePassword运行结果 |