//================================================================================================

20130806_第一次修改    
     
     
     
     
    ccb_david
//================================================================================================

   
休息了一个礼拜,开始自己课后的学习,想起数据结构课程设计里有同学实现了缓慢画点的功能,于是通过联系本人得到了他的源程序。仔细查看他的程序后,在其中发现了一个我以前没接触过的sleep函数,于是我也对了解sleep函数做了一些资料的查找。

   
首先我自己也进行了试验,发现确实在视觉上能减缓画点的速度,那么实现这个功能的实现形式是怎样的呢?为此我询问了我的老师,他告诉我sleep函数的主要功能是让系统暂停这个应用的运行(使用CPU)。由于这个回答比较简洁,为了了解更多关于sleep函数的信息,我在网上查找了一些资料。

首先sleep函数在不同的操作系统下参数的内容是不一样的:
Dos: 

sleep(1); //停留1秒 

delay(100);
//停留100毫秒

Windows: 

Sleep(100); //停留100毫秒 

Linux: 

sleep(1); //停留1秒 

usleep(1000); //停留1毫秒 


其次在windows里Sleep函数的“S”是大写的,其他的都是小写。

接着我查看了sleep函数在WINBASE.H的定义,定义如下:
WINBASEAPI
VOID
WINAPI
Sleep(
    DWORD
dwMilliseconds
    );

通过定义我们知道Sleep函数里参数是双字型参数,且单位为毫秒。




为了测试是否真如资料中所讲Sleep函数的精度能够保证,我编写下面的程序用于测试其精度。

由于我们需要使用for循环,为了循环本身可能存在的误差,我们先将一次循环大致需要的时间计算出来。
检测循环时间源码部分:
#include<iostream>
using namespace std;
#include <windows.h>

#pragma comment(lib, "Winmm.lib")

int main()
{
   
timeBeginPeriod(1);

    int max,min;
    max=0;
    min=500;

    for(int
i=0;i<100;i++)
    {
      DWORD
timeBegin = timeGetTime();//开始时间(毫秒级)

     
for(int j=0; j<100000000;
j++);//用于测算循环一亿次需要花费的时间

      DWORD
timeOver = timeGetTime();//结束时间(毫秒级)

      if(
timeOver-timeBegin > max )
     
  max=timeOver-timeBegin;
      if(
timeOver-timeBegin < min )
     
  min=timeOver-timeBegin;
    }

   
cout<<"max
="<<max<<endl;
   
cout<<"min
="<<min<<endl;

    return 0;
}
经过运行我们可以得到循环一亿次for循环大概花费的时间在222-249毫秒之间,这样估计大约一次for循环花费的时间是2.22-2.49
ns,基本可以排除循环所带来的误差。


检测sleep函数延迟时间源码部分:
#include<iostream>
using namespace std;
#include <windows.h>

#pragma comment(lib, "Winmm.lib")

int main()
{
  timeBeginPeriod(1);//设置定时器的分辨率

  int a[100];
  int x0,y0;
  int x1,y1;
  x1=y1=100;
  x0=y0=0;

  while(x1)//为数组a赋初始值
  {
    a[x0]=0;
    x0++;
    x1--;
  }

  for(int i=0;i<100;i++)
  {
    DWORD timeBegin =
timeGetTime();//开始时间(毫秒级)

    Sleep(50);

    DWORD timeOver =
timeGetTime();//结束时间(毫秒级)

   
a[i]=timeOver-timeBegin;
  }

  //为了保证输出流不影响测试,我们将输出放在测试循环外
  while(y1)//将所有数组里记录的数据全部输出
  {
   
cout<<"第"<<y0+1<<"次用时:"<<a[y0]<<"
毫秒。"<<endl;
    y0++;
    y1--;
  }

  return 0;
}
经过运行我们可以得到100个输出,其中只有1个输出为51其他均为50,根据这些数据,我们可以基本认为,sleep函数的精度基本上可以说在1毫秒左右。

*注:如果讲究严谨,我们还需要考虑三个赋值运算与一个减法运算。但是通过汇编语言层面我们可以知道,赋值与减法运算在寄存器内部进行操作,所以在这个测试中我们基本可以排除赋值运算与减法运算对我们本次测试的影响。





即使有一天在技术上我已经是个能手,请记住自己应有的责任和保持一个真诚交流、始终渴望追求技术的心。
 
     
     
     
     
     
     
     
     
     
     
     
----------ccb_warlock

关于sleep函数的一些问题和资料的更多相关文章

  1. jQuery 2.0.3 源码分析Sizzle引擎 - 编译函数(大篇幅)

    声明:本文为原创文章,如需转载,请注明来源并保留原文链接Aaron,谢谢! 从Sizzle1.8开始,这是Sizzle的分界线了,引入了编译函数机制 网上基本没有资料细说这个东东的,sizzle引入这 ...

  2. probe函数何时调用的

    转自:http://blog.csdn.net/xiafeng1113/article/details/8030248 Linux中 probe函数何时调用的 所以的驱动教程上都说:只有设备和驱动的名 ...

  3. 本函数用来改变目前 php 执行的目录到新的 directory 目录中

    chdir : 改变目录. dir : 目录类别类. closedir : 关闭目录 handle. opendir : 打开目录 handle. readdir : 读取目录 handle. rew ...

  4. c语言之函数指针

    一.基础研究 这里研究的内容是函数指针,需要我们在研究后构造程序来描述函数指针数组的用法和向函数传函数指针的方法. 指针有很多种:整型指针.结构体指针.数组指针等等,它们的本质是它们的值都是一个地址, ...

  5. C51函数的递归调用

    前几天在写C51程序时用到了递归,简单程序如下: void WRITE_ADD(uchar addr,uchar wbyte) { START(); //先发送起始信号 WRITE_BYTE(0xa0 ...

  6. 如何使用getopt()函数解析参数

    最近在写程序的过程中,把一部分时间都花费在程序对参数的处理上.今天听了学长说到getopt函数,才发现原来c里面还有一个专门解决参数处理的函数,查询了相关资料,这里简单总结一下. 使用int main ...

  7. linux中 probe函数的何时调用的?

    点击打开链接 linux中 probe函数何时调用的 所以的驱动教程上都说:只有设备和驱动的名字匹配,BUS就会调用驱动的probe函数,但是有时我们要看看probe函数里面到底做了什么,还有传递给p ...

  8. HashMap中的hash函数

    在写一个HashSet时候有个需求,是判断HashSet中是否已经存在对象,存在则取出,不存在则add添加.HashSet也是通过HashMap实现,只用了HashMap的key,value都存储一个 ...

  9. SQLITE3 使用总结(直接使用C函数)

    转载网址:http://blog.chinaunix.net/uid-8447633-id-3321394.html 前序: Sqlite3 的确很好用.小巧.速度快.但是因为非微软的产品,帮助文档总 ...

随机推荐

  1. Java第二季

    1.封装 (1)概念 将类的某些信息隐藏在类的内部,不允许外部程序直接访问,而是通过该类提供的方法来实现对隐藏信息的操作和访问. (2)封装的实现步骤 2.Java中的访问修饰符 3.继承 (1)Ja ...

  2. IOS 修改UIImage大小

    在iOS中,uiimage没有用于修改大小的属性,要在代码中改变uiimage图片的大小,需要扩展UIImage类,如下: 头文件: #import<UIKit/UIKit.h> @int ...

  3. Mybatis分页插件PageHelper使用

    一. Mybatis分页插件PageHelper使用  1.不使用插件如何分页: 使用mybatis实现: 1)接口: List<Student> selectStudent(Map< ...

  4. 最短路洛谷P2384

    题目背景 狗哥做烂了最短路,突然机智的考了Bosh一道,没想到把Bosh考住了...你能帮Bosh解决吗? 他会给你100000000000000000000000000000000000%10金币w ...

  5. sublime text 3 ctrl+b浏览器启动html

    sublime text 2 和3 都可以快速设置浏览器启动,本人在这里介绍如何不下插件启动浏览器.第一步:打开Tool-->build system  ---> new build sy ...

  6. POST和GET有什么区别?

    1. GET主要用于从服务器查询数据,POST用于向服务器提交数据 2. GET通过URL传递数据,POST通过http请求体传递数据 3. GET传输数据量有限制,不能大于2kb,POST传递的数据 ...

  7. 基于UDP协议的socket编程

    UDP协议特点: 1.无连接.服务端与客户端传输数据之前不需要进行连接,且没有超时重发等机制,只是把数据通过网络发送出去.也正是因为此特点,所以基于UDP协议的socket的客户端在启动之前不需要先启 ...

  8. 使用REST风格架构您需要知道的一些事

    1. REST的由来 2. REST的构成 2.1. 资源 2.2. 资源的表述 2.2.1. MIME(Multipurpose Internet Mail Extensions) 2.2.2. 缓 ...

  9. em标签和strong标签的区别

    今天模拟面试,第一个问题就是这个,然后我回答说就是表示强调,然后老师说还有吗,我说不知道了,然后,就没有然后了... 第一个层次的区别: <em>标签是告诉浏览器把其中的文本表示为强调的内 ...

  10. google C++编程风格指南之头文件的包括顺序

    google C++编程风格对头文件的包括顺序作出例如以下指示: (1)为了加强可读性和避免隐含依赖,应使用以下的顺序:C标准库.C++标准库.其他库的头文件.你自己project的头文件.只是这里最 ...