|
|
No.1 一個由VB編譯引起的錯誤 在VB編譯環(huán)境下,常有這樣種事情發(fā)生,第一次初始化控制卡時,往往正常通過,若中途中斷或意外退出,則再次啟動程序,則初始化時卻找不到控制卡了,有時弄得人很郁悶,一點成熟感都沒有,在沒有別的招的情況下,搞得程序員一怒之下重啟PC才得以好轉(zhuǎn)。然事情卻很讓人不開心。 這個問題是由VB編譯引起的,由于VB是一種解釋語言,其程序運行時被加載的速度不夠快,故會把程序調(diào)用的動態(tài)庫等資源暫放置內(nèi)存,直到VB整個軟件結(jié)束才會釋放。而在調(diào)試控制卡軟件時,由于中途中斷或調(diào)試意外退出,沒有執(zhí)行到控制卡關閉函數(shù),則控制卡資源還未被釋放,故程序再次運行初始化控制卡資源時,則找不到有效的資源了,因而也找不到控制卡了。 解決問題很簡單,關閉整個VB編譯器軟件,以釋放所有資源,再次進入即可。此過程稍為麻煩,但比上重啟PC來講,還是稍有效率一些。
No.2 取位運算 在使用控制卡編程時,常常碰到取位運算的案例,如下面函數(shù): d3000_get_axis_status 在其《軟件手冊》上有對其返回值的每一位進行了詳細說明,即使這樣,有些新手面對具體編程時,一時還轉(zhuǎn)不過彎過來。如:要從返回值內(nèi)判斷原點信號的高低電平狀態(tài)到底該怎樣編程呢,以下列出在C/C++、Basic取位運算的代碼片段,其它狀態(tài)位類同: (注:DMC3000控制卡的原點信號在d3000_get_axis_status的返回值第9位,從0位開始數(shù))
1、 C/C++ DWORD nStatus = d3000_get_axis_status( XCH );//讀取X軸的專用輸入信號 //XCH的值為0
if( (nStatus&(1<<9)) != 0 ) //高電平或低電平 else //低電平或高電平
(用移位方法在《控制卡編程幾招》中有介紹)
2、 Basic
Dim nStatus as long nStatus = d3000_get_axis_status ( XCH ) ‘讀取X軸的專用輸入信號
if (nStatus and &H200) <> 0 then //高電平或低電平 else //低電平或高電平 end if
注意:第9位為1時的十六進制數(shù)值為0x200
No.3 關于大數(shù)平方和平方根溢出的解決方法 平方和平方根的計算常常遇到,一般都會用浮點數(shù)來表示,當計算大數(shù)時,由于電腦內(nèi)部定義的數(shù)據(jù)類型字節(jié)寬有限,總會有溢的可能,如:
double kx = 1000000.0; //一個double在VC++中為64位,在DOS環(huán)境下為32位 double ky = 1000000.0; double len = sqrt( kx * kx + ky * ky );//求兩者的平方和之根
想必上面的表達算式大家都見怪不怪了吧,但很容易溢出哦,要是多次系數(shù),就更容易了,那么到底該如何解決這個問題呢?我們改一下表達算法,也可達到同樣效果,可將溢出的機率大大降低,請看:
double kx = 1000000.0; double ky = 1000000.0;
ky = (ky/kx); //注意變化,實際應用時,要避免kx=0.0
double len = kx * sqrt( 1 + ky * ky ); //想一想,若kx,ky的數(shù)值有效,那么len的值也不會溢出了
No.4 精確定時器的實現(xiàn)(僅用在VC++) MFC提供的定時器OnTimer,雖然可以通過SetTimer設定響應時間間隔,但無論怎樣都不能超過每少20次的調(diào)用頻率,在一些需要精確計時的場合當然就不適合了。API提供一個性能較好的函數(shù)GetTickCount,這個函數(shù)理論上可以跑到毫秒級,但是它的時間積累誤差很大,而且不可以得到更精確的計時。 在《Windows圖形編程》一書當中有封裝好的一個精確計時類,可以根據(jù)CPU的時鐘周期來計時,夠酷吧,然此書有很多人暫未購得,故由本人做一做義務,公布其主要的核心片段,也足夠大家用了,具體大家再根據(jù)需要去完善吧。
typedef __int64 I64; //一個64位整數(shù)類型的定義
I64 GetQueryCount() {//返回當前時鐘周期,若不明白以下語法,就不明白,反正能用就行,在NT下也正常 _asm _emit 0x0F _asm _emit 0x31 }
//取得1秒中的周期計數(shù)值 I64 start = GetQueryCount (); Sleep(1000); I64 stop = GetQueryCount (); //轉(zhuǎn)化成1微秒的計數(shù)值,可根據(jù)需要進行,我在一個軟件當中使用1微秒就夠了 //單位關系:1秒=1000毫秒=1000000微秒 long double fUnit = (long double)(stop-start)*0.000001;//取得1微秒的時種周期值
若你想要達到100微秒中斷一次,則可以寫出下面程序:
I64 nTimers = I64( fUnit * 100 );//將100再轉(zhuǎn)化周期值 I64 nStart = GetQueryCount(); I64 nEnd = nStart;
While( 你的有效循環(huán)條件 ) { nEnd = GetQueryCount(); if( labs(nEnd – nStart) >= nTimers ) { …做你想做的事情,記得你要作的事情不要太復雜,以致于運行的周期超過自己定義的中斷間隔周期。
nEnd = nStart; } else ::DoEvents();//此函數(shù)在我的相關文章有詳解,故不贅述
|
|
狀 態(tài):
離線
公司簡介
產(chǎn)品目錄
|
|
公司名稱:
|
深圳市雷賽智能控制股份有限公司
|
聯(lián) 系 人: |
梁邦敏
|
電 話: |
755-26401178
|
傳 真: |
|
地 址: |
深圳市南山區(qū)登良路天安南油工業(yè)區(qū)2棟3樓 |
郵 編: |
518000 |
主 頁: |
|
|
|
|
|