無窮迴圈

無窮迴圈

以下是一些無窮迴圈的例子。

C語言的無窮迴圈:

#include

main()

{

while(1) {

printf("Infinite Loop\n");//顯示"Infinite Loop"字串

}

}

上述程式會一直顯示"Infinite Loop"字串。

BASIC語言的無窮迴圈:

10 PRINT "Infinite Loop"

20 GOTO 10'跳到行號=10的位置

X86組合語言的例子:

loop:

;空的無窮迴圈,直接跳到"loop"標籤的位置

jmp loop

Python的例子:

while True:

print("Infinite Loop")#顯示"Infinite Loop"字串

邏輯錯誤

编辑

以下是一個Visual Basic無窮迴圈的例子:

dim x as integer

do until x > 5 '根本不會有x>5的情形

x = 1

x = x + 1

loop

每一次執行迴圈時x會先設定為1,然後變為2,因為數值未大於5,所以永遠不會結束。若將x = 1由迴圈內部移到迴圈之前即可以改善此一情形。

有些程序員可能因為不熟悉特定程式語言的語法而造成無窮迴圈,例如以下是一段C語言的程式:

#include

main()

{

int a = 0;

while (a < 10) {

printf("%d\n", a);

if (a = 5) {//a設定為5,進入無窮迴圈

printf("a equals 5!\n");

}

a++;

}

return 0;

}

其預期輸出是數字0至9,其中5和6中間會顯示"a equals 5!",但程序員在編寫程式時將設定用的=運算子及判斷相同的==運算子弄混了,因此程式會在每次執行迴圈時都會將a設定為5,因此變數a永遠無法到達10,此迴圈就變成了無窮迴圈。

现代化的编译器,例如clang,都已经可以检测到这一类的潜在问题并给出警告。[2]

變數處理錯誤

编辑

有時不適當的迴圈結束條件也可能會造成無預期的無窮迴圈,例如以下C語言的例子:

float x = 0.1;

while (x != 1.1) {//可能會因為浮點運算的誤差而出現問題

printf("x = %f\n", x);

x = x + 0.1;

}

在有些作業系統中,上述程式會執行10次迴圈然後結束,但有些系統中,上述程式卻可能會一直執行,無法結束,問題主要在迴圈的結束條件(x != 1.1)要在二個浮點數相等時才結束,結果會依系統處理浮點數的方式而定,只要系統執行10次迴圈後的結果和1.1差一點點,上述程式就會變成無窮迴圈。

若將結束條件改為(x < 1.1)就沒有這個問題,程式可能會多執行一次迴圈,但不會變成無窮迴圈。另一種解決方式則是用一個整數變數作為迴圈變數,再依此變數判斷是否要結束迴圈。

在數值分析程式中也可能會出現無預期的無窮迴圈,例如程式需一直迭代到誤差小於某特定值為止,但若因為運算中的捨去誤差,使得誤差一直無法小於該特定值,就會產生無窮迴圈。

奧爾德森迴圈

编辑

奧爾德森迴圈(Alderson loop)是指一個迴圈有設定結束條件,但因為程式的寫法(多半是編程錯誤),造成永遠無法滿足結束條件,在針對使用者介面程式偵錯時最容易出現這類的問題。

以下C的虛擬碼中有一個奧爾德森迴圈,程式是要計算使用者輸入一串數字的和,使用者輸入0時結束迴圈,但程式中用了不正確的運算符:

sum = 0;

while (true) {

printf("Input a number to add to the sum or 0 to quit");

i = getUserInput();

if (i * 0) { // 若i乘0为真,则使sum加上i的值

sum += i; // 但这不可能发生,因为不论i为何值(i * 0)都是0。如果条件中用的是!=而非*,代码就能正常运行

}

if (sum > 100) {

break; // 终止循环。结束条件存在,但从来没有达到过,因为sum永远不会增加

}

}

「奧爾德森迴圈」來自一個Microsoft Access的程式設計師,他編寫的程式產生一個有模式的对话框,使用者需要回應,程式才能繼續運作,但对话框沒有OK鍵或取消鍵,因此只要此對話窗出現,Access程式就無法繼續運作[3]。

無窮遞迴

编辑

無窮遞迴是一種由递归造成的無窮迴圈。例如以下計算階乘的C語言程式:

unsigned int fac(unsigned int a)

{//n!=n*(n-1)!

return( fac(a-1) * a);

}

一般遞迴的程式會有一特定條件,此條件成立時直接計算結果,而不是透過遞迴來計算結果,若程式中未定義此條件,就會出現無窮遞迴。

無窮遞迴會造成堆疊溢位,而無窮遞迴不會結束,因此也是無窮迴圈的一種。不過若遞迴程式是使用尾端遞迴的處理方式,在有些程式語言(如Scheme)中會優化成迴圈,因此不會造成堆疊溢位。

上述的程式可以修改成沒有無窮遞迴的程式。

unsigned int fac(unsigned int a)

{

if (a == 0) {//定義0!=1

return 1;

}

else {

return( fac(a-1) * a);

}

}

相关推荐

“胤”粤语怎么读?和那些字同音?
趣投必发365

“胤”粤语怎么读?和那些字同音?

🗓️ 07-17 👁️ 9585
全国认证认可信息公共服务平台
趣投必发365

全国认证认可信息公共服务平台

🗓️ 07-09 👁️ 773
如何看待学习这件事 听林曦老师讲如何精进学习力
365bet是什么

如何看待学习这件事 听林曦老师讲如何精进学习力

🗓️ 07-25 👁️ 3202
【史话宝鸡】:虢文化在发源地宝鸡的传承与发展
365bet提款条件

【史话宝鸡】:虢文化在发源地宝鸡的传承与发展

🗓️ 07-15 👁️ 8658
钓友app有哪些
趣投必发365

钓友app有哪些

🗓️ 07-18 👁️ 6572
dnf去哪里整幅
365bet是什么

dnf去哪里整幅

🗓️ 07-30 👁️ 3048
13.4《你在哪里啊,红莲》演唱与赏析.pdf
365bet提款条件

13.4《你在哪里啊,红莲》演唱与赏析.pdf

🗓️ 06-29 👁️ 1884
微博如何快速批量取消关注脚本教程
365bet是什么

微博如何快速批量取消关注脚本教程

🗓️ 07-11 👁️ 2777
正月十八是什么日子
365bet提款条件

正月十八是什么日子

🗓️ 07-31 👁️ 2630
铍金属:核聚变“心脏材料”引爆A股新风口 一、铍金属:战略金属的“硬核价值”铍(Be)作为轻质、高刚度、高热性能的稀有金属,是航空航天、核工业、半导体等尖端领域的...
9158虚拟视频2.4版使用攻略
365bet是什么

9158虚拟视频2.4版使用攻略

🗓️ 08-01 👁️ 7002
有线机顶盒怎么连接wifi 有线机顶盒连接wifi方法【步骤】