国产午夜成人免费看片无遮挡_日本免费xxxx色视频_免费人成网上在线观看_黄网址在线永久免费观看

當前位置:雨林木風下載站 > 技術開發教程 > 詳細頁面

運用delphi創建精確計數器

運用delphi創建精確計數器

更新時間:2022-04-28 文章作者:未知 信息來源:網絡 閱讀次數:

在windows中的很多場合下編程(例如工業控制、游戲)中需要比較精確的記時器,本文討論的是在delphi下實現記時器的若干方法以及它們的精度控制問題。

在delphi中最常用的是timer控件,它的設置和使用都非常方便,理論上它的記時精度可以達到1ms(毫秒)。但是眾所周知的,實際上timer在記時間隔小于50ms之下是精度是十分差的。它只適用于對于精度要求不太高的場合。

       這里作者要介紹的是兩種利用windows api函數實現精確記時的方法。第一中方法是利用高性能頻率記數(作者本人的稱呼)法。利用這種方法要使用兩個api函數queryperformancefrequency和queryperformancecounter。queryperformancefrequency函數獲得高性能頻率記數器的震蕩頻率。

調用該函數后,函數會將系統頻率記數器的震蕩頻率(每毫秒)保存到一個largeinteger中。不過利用該函數在幾臺機器上做過試驗,結果都是1193180。讀者朋友可以在自己的機器上試一下

queryperformancecounter函數獲得系統頻率記數器的震蕩次數,結果也保存到一個largenteger中。  

很顯然,如果在計時中首先使用queryperformancefrequency獲得高性能頻率記數器每毫秒的震蕩次數,然后在計時開始時使用queryperformancecounter函數獲得當前系統頻率記數器的震蕩次數。在計時結束時再調用queryperformancecounter函數獲得系統頻率記數器的震蕩次數。將兩者相減,再將結果除以頻率記數器每毫秒的震蕩次數,就可以獲得某一事件經過的準確時間。(次數除以頻率等于時間)

另外的一種精確記時器的功能是利用多媒體記時器函數(這也是作者的定義,因為這個系列的函數是在winmm.dll中定義并且是為媒體播放服務的)。

實現多媒體記時器首先要使用timesetevent函數建立計時事件。該函數在delphi中的mmsystem.pas中有定義,定義如下:

function timesetevent(udelay, uresolution: uint;

  lpfunction: tfntimecallback; dwuser: dword; uflags: uint): mmresult; stdcall

函數定義中參數udelay定義延遲時間,以毫秒為單位,該參數相當于timer控件的interval屬性。參數uresolution定義記時精度,如果要求盡可能高的精度,要將該參數設置為0;參數lpfunction定義了timesetevent函數的回調函數。該函數相當于一個定時中斷處理函數,每當經過一個udelay長度的時間間隔,該函數就會被調用,編程者可以在該函數中加入相應的處理語句。參數dwuser定義用戶自定義的回調值,該值將傳遞給回調函數。參數uflags定義定時類型,如果要不間斷的記時,該值應設置為1。

如果函數調用成功,在系統中建立了一個多媒體記時器對象,每當經過一個udelay時間后lpfunction指定的函數都會被調用。同時函數返回一個對象標識,如果不再需要記時器則必須要使用timekillevent函數刪除記時器對象。

由于windows是一個多任務的操作系統,因此基于api調用的記時器的精度都會受到其它很多因素的干擾。到底這兩中記時器的精度如何,我們來使用以下的程序進行驗證:

設置三種記時器(timer控件、高性能頻率記數、多媒體記時器)。將它們的定時間隔設置為10毫秒,讓它們不停工作直到達到一個比較長的時間(比如60秒),這樣記時器的誤差會被累計下來,然后同實際經過的時間相比較,就可以得到它們的精度。
下面是具體的檢測程序。

unit unit1;

interface

uses
  windows, messages, sysutils, classes, graphics, controls, forms, dialogs,stdctrls, extctrls,mmsystem;

type
  tform1 = class(tform)
    edit1: tedit;
    edit2: tedit;
    edit3: tedit;
    button1: tbutton;
    button2: tbutton;
    timer1: ttimer;
    procedure formcreate(sender: tobject);
    procedure button1click(sender: tobject);
    procedure timer1timer(sender: tobject);
    procedure button2click(sender: tobject);
  private
    { private declarations }
  public
    { public declarations }
  end;

var
  form1: tform1;
  acttime1,acttime2:cardinal;
  smmcount,stimercount,spcount:single;
  htimeid:integer;
  iten:integer;
  protimecallback:tfntimecallback;

procedure timeproc(utimerid, umessage: uint; dwuser, dw1, dw2: dword) stdcall;

procedure proendcount;

implementation

{$r *.dfm}

//timesetevent的回調函數

procedure proendcount;
begin
  acttime2:=gettickcount-acttime1;
  form1.button2.enabled :=false;
  form1.button1.enabled :=true;
  form1.timer1.enabled :=false;
  smmcount:=60;
  stimercount:=60;
  spcount:=-1;
  timekillevent(htimeid);
end;

procedure timeproc(utimerid, umessage: uint;dwuser, dw1, dw2: dword) stdcall;
begin
  form1.edit2.text:=floattostr(smmcount);
  smmcount:=smmcount-0.01;
end;

procedure tform1.formcreate(sender: tobject);
begin
  button1.caption :='開始倒計時';
  button2.caption :='結束倒計時';
  button2.enabled :=false;
  button1.enabled :=true;
  timer1.enabled :=false;
  smmcount:=60;
  stimercount:=60;
  spcount:=60;
end;

procedure tform1.button1click(sender: tobject);
var
  lgtick1,lgtick2,lgper:tlargeinteger;
  ftemp:single;
begin
  button2.enabled :=true;
  button1.enabled :=false;
  timer1.enabled :=true;
  timer1.interval :=10;
  protimecallback:=timeproc;
  htimeid:=timesetevent(10,0,protimecallback,1,1);
  acttime1:=gettickcount;
  //獲得系統的高性能頻率計數器在一毫秒內的震動次數
  queryperformancefrequency(lgper);
  ftemp:=lgper/1000;
  iten:=trunc(ftemp*10);
  queryperformancecounter(lgtick1);
  lgtick2:=lgtick1;
  spcount:=60;
  while spcount>0 do begin
   queryperformancecounter(lgtick2);
    //如果時鐘震動次數超過10毫秒的次數則刷新edit3的顯示
    if lgtick2 - lgtick1 > iten then begin
            lgtick1 := lgtick2;
            spcount := spcount - 0.01;
            edit3.text := floattostr(spcount);
            application.processmessages;
    end;
  end;
end;

procedure tform1.timer1timer(sender: tobject);

begin
  edit1.text := floattostr(stimercount);
  stimercount:=stimercount-0.01;
end;

procedure tform1.button2click(sender: tobject);

begin
  proendcount;
  //顯示從開始記數到記數實際經過的時間
  showmessage('實際經過時間'+inttostr(acttime2)+'毫秒');
end;

end.

       運行程序,點擊“開始倒記時”按鈕,程序開始60秒倒記時,由于上面的程序只涉及了記時器程序的原理而沒有將錯誤處理加入其中,所以不要等60秒倒記時結束。點擊“結束倒記時”按鈕可以結束倒記時。這時在彈出對話框中會顯示實際經過的時間(單位為毫秒),將三個文本框內的時間乘以1000再加上實際經過的時間,越接近60000,則記時精度越高。

下面是在我的機器上的執行結果。
       從上面的結果看,由delphi的timer控件建立的記時器的精度十分差,無法在實際中使用,而利用高性能頻率記數法和多媒體計數器法的誤差都在1%以下。考慮到程序中在文本框中顯示時間對程序所造成的影響,這個誤差在應用中是完全可以忽略的。
另外在運行程序時作者還發現一個問題,如果在倒記時時拖動窗口,文本框中的顯示都會停止,而當停止窗口拖放后,多媒體記時器顯示會跳過這段時間記時,而其它兩種記時器顯示倒記時卻還是從原來的時間倒數。這說明多媒體記時器是在獨立的線程中運行的,不會受到程序的影響。

綜合上面的介紹和范例,我們可以看到,如果要建立高精度的記時器,使用多媒體記時器是比較好的選擇。而高性能頻率記數法比較適合計算某個耗時十分短的過程所消耗的時間(例如分析程序中某個被多次調用的程序段執行時間以優化程序),因為畢竟高性能頻率記數的理論可以達到微秒級別。timer控件雖然精度比上面兩者差很多,但是它使用方便,在要求不高的場合它還是最佳選擇。

(最后要說的是,以上的結果都是在windows 9x下獲得的,作者在windows 2000下運行該程序時發現,timer控件的精度比在windows 9x下要高出很多,一般誤差在5%以下,這說明windows 2000是一個真正的多任務操作系統。再加上windows nt\2000的穩定性和易用性,在工業控制或實時檢測等領域是一個比較完美的平臺)

溫馨提示:喜歡本站的話,請收藏一下本站!

本類教程下載

系統下載排行

国产午夜成人免费看片无遮挡_日本免费xxxx色视频_免费人成网上在线观看_黄网址在线永久免费观看

  • <label id="pxtpz"><meter id="pxtpz"></meter></label>
      1. <span id="pxtpz"><optgroup id="pxtpz"></optgroup></span>

        日韩福利视频网| 国产精品九色蝌蚪自拍| 久久久久国产一区二区三区四区| 日欧美一区二区| 日韩欧美资源站| 国产九色精品成人porny| 久久久99久久精品欧美| 国产91精品久久久久久久网曝门| 中文字幕亚洲区| 欧美二区在线观看| 国产老肥熟一区二区三区| 国产精品卡一卡二卡三| 在线亚洲免费视频| 精品午夜久久福利影院| 亚洲精品国产一区二区三区四区在线| 在线国产电影不卡| 国产九色精品成人porny | 亚洲三级免费电影| 欧美日韩免费一区二区三区| 青青草97国产精品免费观看 | 一区二区三区不卡视频在线观看| 在线电影院国产精品| 国产99精品在线观看| 亚洲无人区一区| 中文字幕不卡在线播放| 这里只有精品免费| 欧美日韩亚洲综合在线 欧美亚洲特黄一级| 亚洲精品成人少妇| 久久夜色精品国产噜噜av| 在线精品亚洲一区二区不卡| 精品一区二区精品| 亚洲va欧美va人人爽午夜| 国产精品美女久久福利网站| 91精品国产入口在线| 91老师片黄在线观看| 国产美女av一区二区三区| 日本人妖一区二区| 亚洲第一成年网| 亚洲伊人色欲综合网| 亚洲日本免费电影| 国产精品久久三| 日本一区二区三区在线不卡| www精品美女久久久tv| 在线电影一区二区三区| 色狠狠桃花综合| 色狠狠av一区二区三区| 91视频.com| 91亚洲国产成人精品一区二三| 国产激情精品久久久第一区二区| 奇米影视一区二区三区| 亚洲一卡二卡三卡四卡无卡久久| 综合av第一页| 亚洲区小说区图片区qvod| 中文字幕视频一区| 国产精品美女久久久久久久久久久| 精品成人一区二区三区四区| 欧美成人一区二区三区在线观看 | 欧美日韩精品一二三区| 91小视频在线免费看| 9i在线看片成人免费| 不卡av在线网| 色婷婷综合久久久中文一区二区| 99热精品国产| 色域天天综合网| 欧美日韩在线三区| 欧美另类高清zo欧美| 日韩视频在线永久播放| 国产亚洲污的网站| 亚洲欧洲性图库| 亚洲va欧美va国产va天堂影院| 日韩精品久久理论片| 免费一级片91| 国产xxx精品视频大全| 91啪在线观看| 欧美美女bb生活片| 久久精品人人做人人综合 | av亚洲精华国产精华精华| 91亚洲精品久久久蜜桃| 欧美天堂一区二区三区| 欧美日韩国产色站一区二区三区| 91麻豆精品国产91| 久久久.com| 一个色综合av| 国产精选一区二区三区| 欧美一卡二卡在线观看| 国产蜜臀av在线一区二区三区| 中文字幕一区二区三区四区不卡| 亚洲一级不卡视频| 激情综合色播五月| 一本一道综合狠狠老| 精品免费国产二区三区| 亚洲黄色在线视频| 久久草av在线| 91福利在线观看| 久久久美女毛片| 亚洲精品视频免费观看| 精品亚洲成av人在线观看| 97精品国产97久久久久久久久久久久| 欧美精品乱人伦久久久久久| 中文字幕免费观看一区| 美女一区二区在线观看| 欧美在线一区二区| 中文字幕一区二区三区不卡在线 | 国产精品久久久久久久午夜片| 一区二区三区成人| 黄网站免费久久| 精品视频在线免费观看| 欧美国产精品久久| 久久99精品国产麻豆不卡| 欧美午夜电影网| 亚洲欧美在线视频观看| 国产精品自拍三区| 欧美大片一区二区三区| 午夜av一区二区三区| 色悠悠久久综合| 国产精品国产三级国产aⅴ无密码| 青青草原综合久久大伊人精品| 日本久久一区二区| 国产精品伦理在线| 国产成人免费在线观看| 精品国产免费视频| 麻豆91在线看| 日韩视频国产视频| 麻豆一区二区三| 日韩欧美一区二区免费| 亚洲大片一区二区三区| 色婷婷久久久亚洲一区二区三区| 国产欧美日韩一区二区三区在线观看| 久久精品国产99国产精品| 欧美一区二区三区色| 免费在线观看成人| 日韩欧美中文一区二区| 久久97超碰色| 久久久噜噜噜久噜久久综合| 激情综合色丁香一区二区| 日韩精品一区二区三区四区 | 欧美精品一区二区三区蜜桃视频| 三级亚洲高清视频| 欧美一区二区三区在线观看视频| 丝袜美腿高跟呻吟高潮一区| 91麻豆精品91久久久久同性| 免费在线观看视频一区| 精品成人在线观看| 国产精华液一区二区三区| 中文字幕精品一区| 97久久精品人人做人人爽| 亚洲精品国产无套在线观| 欧美视频在线不卡| 日本美女一区二区| 久久综合久久久久88| 欧美色图激情小说| 日韩av成人高清| 精品国产乱码久久久久久闺蜜| 国产精品亚洲一区二区三区在线| 欧美国产欧美亚州国产日韩mv天天看完整| 国产成人精品影视| 一区二区三区四区精品在线视频| 3atv一区二区三区| 懂色av一区二区三区免费观看| 一区二区三区产品免费精品久久75| 欧美日韩国产中文| 国产很黄免费观看久久| 一区二区三区欧美| www精品美女久久久tv| 99r精品视频| 久久国产精品免费| 国产精品久久久99| 制服丝袜av成人在线看| 不卡一区在线观看| 麻豆精品视频在线观看| 亚洲日本一区二区三区| 精品久久五月天| 欧美亚洲一区二区三区四区| 国内精品写真在线观看| 一区二区三区在线免费观看| 精品乱码亚洲一区二区不卡| 97se亚洲国产综合自在线观| 老司机午夜精品99久久| 亚洲天堂精品在线观看| 精品精品欲导航| 欧美日韩免费高清一区色橹橹| 丰满少妇在线播放bd日韩电影| 日日夜夜精品视频免费| 自拍偷拍欧美精品| 久久精品一区二区三区不卡牛牛| 欧美日韩精品系列| 91色porny蝌蚪| 风间由美性色一区二区三区| 另类小说图片综合网| 亚洲国产一区在线观看| 国产精品麻豆网站| 亚洲国产精品ⅴa在线观看| 欧美zozo另类异族| 777精品伊人久久久久大香线蕉| 欧美中文字幕一区| av不卡在线播放| 成人国产亚洲欧美成人综合网| 精品一区二区免费视频| 久久国产尿小便嘘嘘尿| 毛片不卡一区二区|