線上訂房服務-台灣趴趴狗聯合訂房中心
發文 回覆 瀏覽次數:3320
推到 Plurk!
推到 Facebook!

如何暫停才不會讓電腦以為當機

答題得分者是:orson
P.D.
版主


發表:603
回覆:4038
積分:3874
註冊:2006-10-31

發送簡訊給我
#1 引用回覆 回覆 發表時間:2002-09-09 21:41:26 IP:210.85.xxx.xxx 未訂閱
請問各位!    我現在有一個需求,     我設計一個迴圈的程式執行, 但必須在迴圈中可以該使用者按下一個key就暫停迴圈的執行, 等使用者要恢復執行再按一個key繼續往未完成的迴圈做下去, 迴圈內的作業程序頗為複雜,     在我的迴圈內有加 Application.ProcessMessage, 在 onkeydown 加入 if key= xxxx then TForm1.StopRun....(暫停procedure)    我現在遇到的是    1.當執行暫停時, 畫面不可以有任何新視窗的顯示, 例如跳出一個視窗, label顯示系統暫停, 然後有一個button按下去可以繼續, 這個動作是不可以被設計的 所以暫停時畫面有如當機(當然不是真的當機, 只是程式停在按下去那一刻的流程) 2.在沒有任何視窗及button可以恢復繼續的情況下, 如何該使用者再按下一個key通知系統繼續 3.我不能在StopRun 的 procedure 中這樣寫(以下一些變數是我定義的)   
  i:=1;
  while key=recall do begin
     Application.ProcessMessage;
     inc(i);
  end;
  
因為我不知道user會停多久, inc()可能會造成 stack overflow 我也不能使用 sleep, 情況同上 4.win98有一個很不好的行為, 如果程式停太久沒有任何R/W, WIN98會自動發出沒有回應的訊息(當你按 ALT-CTRL-DEL 可以看到), 然後其實系統並未當機只是暫停, 如何才能避免這個情況發生 以上希望各位前輩可以看得懂! 謝謝!
orson
中階會員


發表:5
回覆:135
積分:58
註冊:2002-07-11

發送簡訊給我
#2 引用回覆 回覆 發表時間:2002-09-09 23:43:45 IP:61.219.xxx.xxx 未訂閱
在主畫面放個timer timer.ontimer begin application.processmessages; end; 就不會有無回應的狀況了 要按特殊鍵結束 TForm有一個property : KeyPreview就是你要的了(一半)
P.D.
版主


發表:603
回覆:4038
積分:3874
註冊:2006-10-31

發送簡訊給我
#3 引用回覆 回覆 發表時間:2002-09-10 11:05:36 IP:210.85.xxx.xxx 未訂閱
引言: 在主畫面放個timer timer.ontimer begin application.processmessages; end; 就不會有無回應的狀況了 要按特殊鍵結束 TForm有一個property : KeyPreview就是你要的了(一半)
謝謝 orson 說明, 那我在主form已經有一個timer專門在顯示目前時間的功能(每秒偵測一次), 是否也如同你提供的功能(但沒有Application.ProcessMessage)! 另外, 不知 orson 對我所提到的暫停及恢復暫停(在上面所說的條件設定下)有沒有更好的設計方法? 謝謝!
hagar
版主


發表:143
回覆:4056
積分:4445
註冊:2002-04-14

發送簡訊給我
#4 引用回覆 回覆 發表時間:2002-09-10 11:14:40 IP:211.22.xxx.xxx 未訂閱
不知道這樣可不可以:
begin
  repeat
    Application.ProcessMessages;
  until { You want it stop };
end;
andersonhsieh
版主


發表:33
回覆:531
積分:439
註冊:2002-06-10

發送簡訊給我
#5 引用回覆 回覆 發表時間:2002-09-10 11:15:01 IP:211.20.xxx.xxx 未訂閱
給你一個建議 1.當按下特定鍵時秀出一視窗(用SHOWMODULE,因為SHOWMODULE會搶走主控權,原來的程式會暫時執行等待視窗關閉)告知使用者現在是暫停狀態,當該視窗關閉時又會繼續下面的動作,這樣應該就可以解決你的問題 @@~~飛翔在天際的精靈~~@@
------
@@~~飛翔在天際的精靈~~@@
P.D.
版主


發表:603
回覆:4038
積分:3874
註冊:2006-10-31

發送簡訊給我
#6 引用回覆 回覆 發表時間:2002-09-10 11:58:21 IP:210.85.xxx.xxx 未訂閱
引言: 給你一個建議 1.當按下特定鍵時秀出一視窗(用SHOWMODULE,因為SHOWMODULE會搶走主控權,原來的程式會暫時執行等待視窗關閉)告知使用者現在是暫停狀態,當該視窗關閉時又會繼續下面的動作,這樣應該就可以解決你的問題 @@~~飛翔在天際的精靈~~@@
sorry! 版主! 我上面的第一個條件就是不能秀出任何訊息, 這是客戶要求的, 我必須遵從, 如果可以用視窗的話, 我就不用這麼麻煩了!
P.D.
版主


發表:603
回覆:4038
積分:3874
註冊:2006-10-31

發送簡訊給我
#7 引用回覆 回覆 發表時間:2002-09-10 12:01:30 IP:210.85.xxx.xxx 未訂閱
引言: 不知道這樣可不可以:
begin
  repeat
    Application.ProcessMessages;
  until { You want it stop };
end;
謝謝! 我試試看!
magicang
一般會員


發表:0
回覆:3
積分:0
註冊:2002-08-31

發送簡訊給我
#8 引用回覆 回覆 發表時間:2002-09-10 17:58:20 IP:203.121.xxx.xxx 未訂閱
Add sleep(xx) inside the loop
P.D.
版主


發表:603
回覆:4038
積分:3874
註冊:2006-10-31

發送簡訊給我
#9 引用回覆 回覆 發表時間:2002-09-10 21:49:35 IP:210.85.xxx.xxx 未訂閱
引言: Add sleep(xx) inside the loop
不能使用sleep, 這也是我的條件之一
andersonhsieh
版主


發表:33
回覆:531
積分:439
註冊:2002-06-10

發送簡訊給我
#10 引用回覆 回覆 發表時間:2002-09-10 22:01:35 IP:211.23.xxx.xxx 未訂閱
不好意思修改一下hagar的程式,你可以試試以下程式碼
IF KEY=特定KEY THEN
 REPRAT_FALG := TRUE;
  WHILE REPRAT_FALG DO
  BEGIN
    Application.ProcessMessages;
  END;    在FORM的ONKEYDOWN寫
IF KEY=特定KEY THEN
 REPRAT_FALG := FALSE;
FORM的KeyPreview一定要設定為TRUE @@~~飛翔在天際的精靈~~@@ 發表人 - andersonhsieh 於 2002/09/10 22:04:26
------
@@~~飛翔在天際的精靈~~@@
syntax
尊榮會員


發表:26
回覆:1139
積分:1258
註冊:2002-04-23

發送簡訊給我
#11 引用回覆 回覆 發表時間:2002-09-11 03:50:34 IP:203.204.xxx.xxx 未訂閱
引言: 不好意思修改一下hagar的程式,你可以試試以下程式碼
IF KEY=特定KEY THEN
 REPRAT_FALG := TRUE;
  WHILE REPRAT_FALG DO
  BEGIN
    Application.ProcessMessages;
  END;    在FORM的ONKEYDOWN寫
IF KEY=特定KEY THEN
 REPRAT_FALG := FALSE;
FORM的KeyPreview一定要設定為TRUE @@~~飛翔在天際的精靈~~@@ 發表人 - andersonhsieh 於 2002/09/10 22:04:26
大家都繞在一個回圈加 Application.ProcessMessage內轉..... 問題的本質在哪 ? 解決的方式 真的只能這樣嗎 ? 提供你一個反向的思考 1.把你的工作設計成可以用一個procedure 或function 叫用 2.叫用一次就做一步 3.再用一個迴圈來執行(不是暫停) 4.在使用者按下執行的 Key 時,迴圈就會被叫用啟動,這樣就可以一直處理你要的是 5.在使用者按下暫停key後,就會跳出回圈,這樣不就暫停了,同時也不會被視為沒有回應 如果你的程式無法在公開的板上討論,我們可以私下討論,我只是學生,不用擔心會洩漏你的機密,不過也因為我是學生,所以能力的也有限,至於幫不幫得上,嗯!聊了才知道 !! syntax@giga.net.tw
天外來客
初階會員


發表:22
回覆:199
積分:44
註冊:2001-11-27

發送簡訊給我
#12 引用回覆 回覆 發表時間:2002-09-11 23:52:49 IP:211.22.xxx.xxx 未訂閱
寫成Multithread比較實際啦
P.D.
版主


發表:603
回覆:4038
積分:3874
註冊:2006-10-31

發送簡訊給我
#13 引用回覆 回覆 發表時間:2002-09-12 17:22:36 IP:210.85.xxx.xxx 未訂閱
引言: 寫成Multithread比較實際啦
這段我並未接觸過, 不知如何下手, 可否請教範例?
syntax
尊榮會員


發表:26
回覆:1139
積分:1258
註冊:2002-04-23

發送簡訊給我
#14 引用回覆 回覆 發表時間:2002-09-13 02:45:47 IP:203.204.xxx.xxx 未訂閱
用 Multithread 的話 主程式是會繼續運作的喔! 而那個暫停的 Thread 還是會像當了一樣不理你的
P.D.
版主


發表:603
回覆:4038
積分:3874
註冊:2006-10-31

發送簡訊給我
#15 引用回覆 回覆 發表時間:2002-09-13 10:51:37 IP:210.85.xxx.xxx 未訂閱
引言: 用 Multithread 的話 主程式是會繼續運作的喔! 而那個暫停的 Thread 還是會像當了一樣不理你的
喔! 謝謝說明, 我需要的是主程式必須能暫停而且不會引發當機, 目前我使用 hagar版主的方式來做, 不過因為我的Loop 裡面已經大量使用Application.ProcessMessage(不單是暫停而已, 還有連結控制系統中也使用很多, 至少有15個以上), 已經是到氾濫的程度, 所以我比較擔心的是一旦啟動如此的暫停模式會造成不可收拾的當機, 但因程式受業主合約保護, 我無法丟上去給各位指正(而且內含大量的控制系統, 沒有那些元件也無法run), 所以謝謝大家的支援! 發表人 - P.D. 於 2002/09/13 10:52:45
orson
中階會員


發表:5
回覆:135
積分:58
註冊:2002-07-11

發送簡訊給我
#16 引用回覆 回覆 發表時間:2002-09-13 12:13:27 IP:211.74.xxx.xxx 未訂閱
引言:
引言: 在主畫面放個timer timer.ontimer begin application.processmessages; end; 就不會有無回應的狀況了 要按特殊鍵結束 TForm有一個property : KeyPreview就是你要的了(一半)
謝謝 orson 說明, 那我在主form已經有一個timer專門在顯示目前時間的功能(每秒偵測一次), 是否也如同你提供的功能(但沒有Application.ProcessMessage)! 另外, 不知 orson 對我所提到的暫停及恢復暫停(在上面所說的條件設定下)有沒有更好的設計方法? 謝謝!
你必須在timer裏去做至少一次的processmessages. 因為timer本身也是一個windows message. 你在timer裡面做的Visible Component的更新呢 他也需要一個windows message來讓自己重畫 可視元件裏都有相對應的method像是invalidate,update等等 元件提供這些功能是因為讓元件重畫的message在windows message queue裡面 是屬於低等級的 而且是可忽略的 那多呼叫幾次application.processmessages就好了 不是嗎 是可以啦 只是要注意你有沒有一些event重複進入會不會出狀況 然後你就可以在主畫面的onKeyDown去判斷你要的按鍵是不是到了 OnKeyDown應該會傳個key的參數給你吧 你可以寫個像這樣的東西 if key = ord('A') then bSuspend := True; 然後呢 最重要的是你那個處理資料的迴圈 就可以寫成 function xxxx; begin bSuspend := False; while not bSuspend do begin // do whatever you want. end; end; 這樣應該就可以了 除非你是在等資料庫回應 那就是另一回事了 --- 忘了講 以上言論 均未經測試 也就是說 我沒先run過喔 因為我現在這台電腦是空的 哈哈 It should work. 發表人 - orson 於 2002/09/13 12:18:10
P.D.
版主


發表:603
回覆:4038
積分:3874
註冊:2006-10-31

發送簡訊給我
#17 引用回覆 回覆 發表時間:2002-09-13 18:35:23 IP:210.85.xxx.xxx 未訂閱
再次謝謝orson兄的說明, 目前我也是用這個方式在處理, 暫時測試是還沒有出現大問題!
zycagod
一般會員


發表:0
回覆:14
積分:12
註冊:2002-07-08

發送簡訊給我
#18 引用回覆 回覆 發表時間:2002-09-20 16:46:43 IP:61.220.xxx.xxx 未訂閱
引言:
引言: 用 Multithread 的話 主程式是會繼續運作的喔! 而那個暫停的 Thread 還是會像當了一樣不理你的
喔! 謝謝說明, 我需要的是主程式必須能暫停而且不會引發當機, 目前我使用 hagar版主的方式來做, 不過因為我的Loop 裡面已經大量使用Application.ProcessMessage(不單是暫停而已, 還有連結控制系統中也使用很多, 至少有15個以上), 已經是到氾濫的程度, 所以我比較擔心的是一旦啟動如此的暫停模式會造成不可收拾的當機, 但因程式受業主合約保護, 我無法丟上去給各位指正(而且內含大量的控制系統, 沒有那些元件也無法run), 所以謝謝大家的支援! 發表人 - P.D. 於 2002/09/13 10:52:45
如果不想濫用ProcessMessages 可用HandleMessage 然後Timer看你要不要加入 SendMessage(Self.Handle,0,0,0)
P.D.
版主


發表:603
回覆:4038
積分:3874
註冊:2006-10-31

發送簡訊給我
#19 引用回覆 回覆 發表時間:2002-09-20 22:15:35 IP:210.85.xxx.xxx 未訂閱
引言: 如果不想濫用ProcessMessages 可用HandleMessage 然後Timer看你要不要加入 SendMessage(Self.Handle,0,0,0)
哦! 這倒是蠻新鮮的, 可否再指教一二, 或是否有Sample可參考! 謝謝!
zycagod
一般會員


發表:0
回覆:14
積分:12
註冊:2002-07-08

發送簡訊給我
#20 引用回覆 回覆 發表時間:2002-09-25 10:19:58 IP:203.70.xxx.xxx 未訂閱
引言:
引言: 如果不想濫用ProcessMessages 可用HandleMessage 然後Timer看你要不要加入 SendMessage(Self.Handle,0,0,0)
哦! 這倒是蠻新鮮的, 可否再指教一二, 或是否有Sample可參考! 謝謝!
ProcessMessages好像是一值會去Queue Pooling HandleMessage 好像是自己的Handle有訊息才會往下作...否則會停在那行 我通常把Timer設50ms 然後SendMessage給自己而已...
ericosur
一般會員


發表:0
回覆:15
積分:8
註冊:2002-08-08

發送簡訊給我
#21 引用回覆 回覆 發表時間:2002-09-27 01:23:07 IP:61.61.xxx.xxx 未訂閱
會被作業系統標示為「無回應」的原因是那個行程 經過了某一段特定的時間都沒有去處理那些 window message 可能是真的當了,也有可能是作大量的運算或IO等等 忘了去處理 message
鈴鐺
初階會員


發表:33
回覆:81
積分:35
註冊:2002-03-13

發送簡訊給我
#22 引用回覆 回覆 發表時間:2002-10-23 11:56:06 IP:61.220.xxx.xxx 未訂閱
我認為會被系統認為當機的原因, 就是沒處理 windows message. 所以每隔一段時間去做 Application.ProcessMessage 是對的. 第二個建議是, 程式若真的要暫停, 等待按鍵, 這時最好加入 sleep. 就算是 sleep 0.幾秒也可以,這樣子 CPU load 才不會總是 100%.
系統時間:2024-11-24 14:59:19
聯絡我們 | Delphi K.Top討論版
本站聲明
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。
2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。
3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇!