Sonsuz döngü - Infinite loop

Gelen bilgisayar programlama , bir sonsuz döngü (veya sonsuz döngü ), yazıldığı gibi, hiç durmadan devam edecek bir dış müdahale ortaya çıkmadığı sürece ( "fişini çekin") bir talimatlar dizisidir. Kasıtlı olabilir.

genel bakış

Bu, şunlardan farklıdır:

  • "durdurulana veya kesintiye uğrayana kadar aynı yönergeleri sürekli olarak çalıştıran bir tür bilgisayar programı."

Aşağıdaki sözde kodu göz önünde bulundurun :

how_many = 0
while is_there_more_data() do
    how_many = how_many + 1
end
display "the number of items counted = " how_many

Aynı komutlar , durdurulana veya kesintiye uğrayana kadar sürekli olarak çalıştırıldı . . . tarafından YANLıŞ fonksiyonu ile bir noktada döndü is_there_more_data .

Buna karşılık, aşağıdaki döngü kendi kendine bitmeyecektir:

birds = 1
fish = 2
while birds + fish > 1 do
    birds = 3 - birds
    fish = 3 - fish
end

kuşlar sırayla 1 veya 2, balıklar sırayla 2 veya 1 olur. Harici bir müdahale olmadıkça ("fişi çekin") döngü durmaz.

Detaylar

Bir sonsuz döngü bir talimatlar dizisidir bilgisayar programı nedeniyle ya sonsuz döngüler döngü karşılanması asla bir veya yeniden başlamak için döngü neden olan bir, bir sonlandırma durumu olan. İşbirliğine dayalı çoklu göreve sahip eski işletim sistemlerinde , sonsuz döngüler normalde tüm sistemin yanıt vermemesine neden oluyordu. Artık yaygın olan önleyici çoklu görev modeliyle, sonsuz döngüler genellikle programın tüm kullanılabilir işlemci zamanını tüketmesine neden olur, ancak genellikle kullanıcı tarafından sonlandırılabilir. Meşgul bekleme döngülerine bazen "sonsuz döngüler" de denir. Sonsuz döngüler, bir bilgisayarın " donmasının " olası nedenlerinden biridir ; diğerleri thrashing , kilitlenme ve erişim ihlallerini içerir .

Amaçlanan ve istenmeyen döngü

Döngü, belirli bir koşul karşılanana kadar bir dizi talimatın tekrarlanmasıdır. Döngünün bazı doğal özelliklerinden dolayı koşul hiçbir zaman karşılanmadığında sonsuz bir döngü oluşur.

kasıtlı döngü

Bunun istenen davranış olduğu birkaç durum vardır. Örneğin, kartuş tabanlı oyun konsollarındaki oyunların ana döngüsünde genellikle çıkış koşulu yoktur, çünkü programın çıkacağı bir işletim sistemi yoktur; döngü, konsol kapatılana kadar çalışır.

Modern etkileşimli bilgisayarlar, bilgisayarın kullanıcı girdisini veya cihaz etkinliğini sürekli olarak izlemesini gerektirir, bu nedenle bazı temel düzeyde , cihaz kapatılana veya sıfırlanana kadar devam etmesi gereken sonsuz bir işlem boşta döngüsü vardır. In Apollo Rehberlik Bilgisayar , örneğin, bu dış döngü Exec programında bulunan edildi ve bilgisayar döngü basitçe "bilgisayar etkinliği" gösterge ışığı kapatmak olacak bir kukla işi aday olacağını bunu yapmak için kesinlikle hiçbir başka iş olsaydı.

Modern bilgisayarlar ayrıca tipik olarak, çöktüğünde işlemciyi veya anakart devresini çalıştıran saatleri durdurmaz. Bunun yerine, operatöre mesaj görüntüleyen bir hata durumuna geri dönerler ve kullanıcının devam etmek için bir komut istemine yanıt vermesini veya cihazı sıfırlamasını bekleyen sonsuz bir döngüye girerler.

Çoklu iş parçacığı

Çok iş parçacıklı programlarda, bazı iş parçacıkları, tüm programın sonsuz bir döngüde sıkışmasına neden olmadan sonsuz döngüler içinde yürütülebilir. Ana iş parçacığı çıkarsa, işlemin tüm iş parçacıkları zorla durdurulur, böylece tüm yürütme sona erer ve işlem/program sona erer. Sonsuz döngülerin içindeki iş parçacıkları "temizlik" görevlerini gerçekleştirebilir veya giriş için bekleyen (soket/sıradan) bloke durumda olabilir ve her giriş alındığında yürütmeye devam edebilir.

kasıtsız döngü

Bu terim çoğu zaman amaçlanan sonucun bu olmadığı durumlar için kullanılır; yani, bu bir hata olduğunda . Bu tür hatalar en çok acemi programcılar arasında yaygındır, ancak nedenleri oldukça belirsiz olabileceğinden deneyimli programcılar tarafından da yapılabilir.

Örneğin, yaygın bir neden, programcının bağlantılı liste veya ağaç gibi bir veri yapısındaki düğüm dizisini yinelemeyi ve her düğüm için döngü kodunu bir kez yürütmeyi istemesidir. Yanlış oluşturulmuş bağlantılar , veri yapısında, bir düğümün dizide daha önce meydana gelen bir diğerine bağlandığı bir referans döngüsü oluşturabilir . Bu, veri yapısının bir kısmını bir halka haline getirir ve saf kodun sonsuza kadar dönmesine neden olur.

Çoğu sonsuz döngü, kodun yakından incelenmesiyle bulunabilirken, belirli bir programın durup durmayacağını veya sonsuza kadar çalışıp çalışmayacağını belirlemek için genel bir yöntem yoktur ; bu kararlaştırılamazlık ait durdurulması problemi .

kesinti

Sistem yanıt verdiği sürece, işleme bir sinyal göndererek ( Unix'teki SIGINT gibi ) veya işlemciye bir kesinti göndererek sonsuz döngüler genellikle kesintiye uğrayabilir ve mevcut işlemin durdurulmasına neden olabilir. Bu, bir görev yöneticisinde , Control-C komutuyla bir terminalde veya kill komutu veya sistem çağrısı kullanılarak yapılabilir . Ancak, süreç sinyallere yanıt vermeyebileceğinden veya işlemci Cyrix koma hatası (bir talimat ardışık düzenindeki kesintisiz talimatların üst üste gelmesinden kaynaklanan) gibi kesintisiz bir durumda olabileceğinden, bu her zaman işe yaramaz . Bazı durumlarda, SIGKILL gibi diğer sinyaller , sürecin yanıt vermesini gerektirmediğinden çalışabilirken, diğer durumlarda döngü, sistem kapanmadan sonlandırılamaz.

Dil desteği

Sonsuz döngüler, çeşitli kontrol akışı yapıları kullanılarak uygulanabilir . En yaygın olarak, yapılandırılmamış programlamada bu geri atlamadır ( goto ), yapılandırılmış programlamada bu, koşul atlanarak veya açıkça true olarak ayarlanarak asla bitmeyecek şekilde ayarlanmış belirsiz bir döngüdür ( while döngüsü ) while (true) ....

Bazı diller, genellikle belirsiz bir döngüden koşulu atlayarak, sonsuz döngüler için özel yapılara sahiptir. Örnekler arasında Ada ( loop ... end loop), Fortran ( DO ... END DO), Go ( for { ... }), Ruby ( loop do ... end) ve Rust ( loop { ... }) bulunur.

Kasıtlı sonsuz döngü örnekleri

Basit bir örnek ( C'de ):

#include <stdio.h>

int main()
{
  for (;;) // or equivalently, while (1)
    ;  
  return 0;
}

for (;;)Sonsuz döngü formu gelenekseldir, standart referans The C Programming Language'de görünür ve genellikle "sonsuza kadar" keskin bir şekilde telaffuz edilir.

Bu, durmadan "Sonsuz Döngü" yazdıracak bir döngüdür.

1980'lerde dönemi içinde benzer bir örnek BASIC :

10 PRINT "INFINITE LOOP"
20 GOTO 10

DOS toplu iş dosyalarında benzer bir örnek :

:A
echo Infinite Loop
goto :A

Burada döngü oldukça açıktır, çünkü son satır koşulsuz olarak yürütmeyi ilk satıra geri gönderir.

Java'da bir örnek

while (true) {
    System.out.println("Infinite Loop");
}

Bourne Again Shell'de bir örnek

for ((;;)); do
	echo "Infinite Loop"
done

Rust'ta bir örnek

loop {
    println!("Infinite loop");
}

Kasıtsız sonsuz döngü örnekleri

Matematiksel hatalar

Visual Basic'te sonsuz döngüye bir örnek :

dim x as integer
do while x < 5
  x = 1
  x = x + 1
loop

Bu x, hiçbir zaman 5'ten büyük olmayacağı bir durum yaratır , çünkü döngü kodunun başlangıcında x1 değeri verilir, bu nedenle döngü her zaman 2'de biter ve döngü asla kırılmaz. Bu, x = 1komutu döngünün dışına taşıyarak düzeltilebilir . Esasen bu sonsuz döngünün yaptığı şey, bir bilgisayara 5'e ulaşılana kadar 1'e 1 eklemeye devam etmesi talimatını vermektir. 1+1 her zaman 2'ye eşit olduğu için bu asla olmayacak.

Bazı dillerde, programcıların matematiksel sembollerle ilgili kafa karışıklığı, kasıtsız bir sonsuz döngüye yol açabilir. Örneğin, C'de bir pasaj :

#include <stdio.h>

int main(void)
{
   int a = 0;
   while (a < 10) {
      printf("%d\n", a);
      if (a = 5)
         printf("a equals 5!\n");
      a++;
   }
   return 0;
}

Beklenen çıktı, araya "a eşittir 5!" eklenerek 0'dan 9'a kadar olan sayılardır. 5 ile 6 arasında. Ancak if (a = 5)yukarıdaki satırda " ", programcı = (atama) operatörünü == (eşitlik testi) operatörüyle karıştırmıştır. Bunun yerine, aprogramın bu noktasında 5 değerini atayacaktır . Böylece aasla 10'a ilerleyemez ve bu döngü sonlandırılamaz.

Yuvarlama hataları

AMD Turion işlemcide C çıkışı :
x = 0.10000000149011611938
x = 0,20000000298023223877
x = 0.30000001192092895508
x = 0,40000000596046447754
x = 0,500000000000000000000
x = 0,60000002384185791016
x = 0.7000004768371582031
x = 0.8000000715255373047
x = 0.90000009536743164062
x = 1.0000011920928955078
x = 1.10000014305114746094
x = 1.20000016689300537109
...

Sonlandırma koşulunun değerlendirilmesinde beklenmeyen davranışlar da bu soruna neden olabilir. İşte C'de bir örnek :

float x = 0.1;
while (x != 1.1) {
  printf("x = %22.20f\n", x);
  x += 0.1;
}

Bazı sistemlerde bu döngü beklendiği gibi on kez yürütülür, ancak diğer sistemlerde asla sona ermez. Sorun, döngü sonlandırma koşulunun (x != 1.1) iki kayan nokta değerinin tam eşitliğini test etmesidir ve kayan nokta değerlerinin birçok bilgisayarda temsil edilme şekli bu testi başarısız kılacaktır, çünkü bunlar 0.1 değerini tam olarak temsil edemezler, böylece her artışta yuvarlama hataları ortaya çıkar (bkz. kutu).

Aynı şey Python'da da olabilir :

x = 0.1
while x != 1:
    print(x)
    x += 0.1

Eşitlik veya eşitsizlik testlerinin beklenmedik bir şekilde başarısız olma olasılığı nedeniyle, kayan noktalı değerlerle uğraşırken büyüktür veya küçüktür testlerini kullanmak daha güvenlidir. Örneğin, x1,1'e eşit olup olmadığını test etmek yerine, (x <= 1.0) veya (x < 1.1) olup olmadığı test edilebilir, bunlardan herhangi birinin sınırlı sayıda yinelemeden sonra çıkması kesindir. Bu özel örneği düzeltmenin başka bir yolu, gerçekleştirilen yinelemelerin sayısını sayarak döngü indeksi olarak bir tamsayı kullanmaktır .

Benzer bir problem, sayısal analizde sıklıkla meydana gelir : belirli bir sonucu hesaplamak için, hata seçilen toleranstan daha küçük olana kadar bir yinelemenin gerçekleştirilmesi amaçlanır. Ancak yineleme sırasındaki yuvarlama hataları nedeniyle, belirtilen toleransa asla ulaşılamaz ve bu da sonsuz bir döngüye neden olur.

Çok partili döngüler

Sonsuz bir döngü, etkileşime giren birkaç öğeden kaynaklanabilir. İsteği anlamıyorsa, her zaman bir hata mesajıyla yanıt veren bir sunucu düşünün. Sunucusunun kendisi içinde sonsuz bir döngü için bir olasılık da, bir sistem iki tanesi (ihtiva A ve B sonsuz) ilmek: eğer bir bilinmeyen tipte bir mesaj alır B , daha sonra bir bir hata iletisi ile yanıt B ; eğer B hata mesajı anlamıyor, bu yanıtlar A kendi hata mesajı ile; eğer bir hata mesajı anlamıyor B , bu böyle devam henüz başka hata mesajı ve gönderir.

Böyle bir durumun yaygın bir örneği, bir e-posta döngüsüdür . E-posta döngüsüne bir örnek, birinin yanıtsız gelen kutusundan posta alması, ancak otomatik yanıtın açık olmasıdır. Yanıt yok gelen kutusuna yanıt verecekler ve "bu yanıt yok gelen kutusudur" yanıtını tetikleyecekler. Bu, kullanıcıya gönderilir, kullanıcı daha sonra yanıtsız gelen kutusuna otomatik bir yanıt gönderir ve bu böyle devam eder.

Sözde sonsuz döngüler

Sözde sonsuz döngü, sonsuz gibi görünen ama aslında çok uzun bir döngüdür.

Çok büyük sayılar

bash'ta bir örnek :

for x in $(seq 1000000000); do
#loop code
done

İmkansız sonlandırma koşulu

Bir örnek döngüsü içinde C :

unsigned int i;
for (i = 1; i != 0; i++) {
  /* loop code */
}

Görünen o ki, bu sonsuza kadar devam edecek, ancak aslında değeri ien sonunda a'da depolanabilen maksimum değere ulaşacak unsigned intve bu sayıya 1 eklemek, döngüyü kırarak 0'a sarılacak. Gerçek limit, kullanılan isistem ve derleyicinin ayrıntılarına bağlıdır . İle keyfi kesinlikte aritmetik , bu döngü bilgisayarın kadar devam edeceğini bellek olabilir artık bekletme i. Eğer ibir tamsayı imzalanan yerine işaretsiz bir tamsayı yerine, taşma tanımsız olacaktır. Bu durumda, derleyici kodu sonsuz bir döngüye optimize edebilir.

sonsuz özyineleme

Sonsuz yineleme kaynaklanır sonsuz döngü özel bir durumudur özyineleme .

VBA'daki aşağıdaki örnek, bir yığın taşması hatası döndürür :

Sub Test1()
    Call Test1
End Sub

Break ifadesi

Bir " while (true)" döngüsü ilk bakışta sonsuz gibi görünür, ancak döngüden bir break deyimi veya return deyimi yoluyla kaçmanın bir yolu olabilir . PHP'de örnek :

while (true) {
    if ($foo->bar()) {
        return;
    }
}

alderson döngüsü

Alderson döngüsü , bir çıkış koşulunun mevcut olduğu, ancak kodun mevcut uygulamasında, genellikle bir programcının hatası nedeniyle erişilemeyen sonsuz bir döngü için nadir bir argo veya jargon terimidir. Bunlar en yaygın olanıdır ve kullanıcı arabirimi kodunda hata ayıklarken görünür .

Programın, sıfır verilene kadar kullanıcı tarafından verilen sayıları toplamasının beklendiği, ancak programcının yanlış operatörü kullandığı bir Alderson döngüsünün C benzeri bir sözde kod örneği:

int sum = 0;
int i;
while (true) {
   printf("Input a number to add to the sum or 0 to quit");
   i = getUserInput();
   if (i * 0) { // if i times 0 is true, add i to the sum. Note: ZERO means FALSE, Non-Zero means TRUE. "i * 0" is ZERO (FALSE)!
      sum += i; // sum never changes because (i * 0) is 0 for any i; it would change if we had != in the condition instead of *
   }
   if (sum > 100) {
      break;    // terminate the loop; exit condition exists but is never reached because sum is never added to
   }
}

Terim iddia edilen bir programcı (soyadı Alderson) adını aldı kim 1996 yılında had oluşturulan kodlanmış bir kalıcı iletişim kutusu içinde Microsoft Access bir OK veya bu suretle kutu geldi her tüm programı devre dışı bırakarak, İptal düğmesine görülmemektedir.

Ayrıca bakınız

Referanslar

  1. ^ "Sonsuz döngü sözlük tanımı" .
  2. ^ "Sonsuz döngü nedir (sonsuz döngü)" .
  3. ^ Denise Caruso (16 Ağustos 1999). "Aşırı Askı Yükü, İnternet Hisse Senetleri için Engebeli Yolculuk Yaratıyor" . New York Times .
  4. ^ "Kodlar ve Modlar: Belgesel Kültürün Karakteri" . Akış Günlüğü . Kasım 2014. sonsuz bir döngü, eksik olan bir döngüdür .. bir çıkış koşulu
  5. ^ ayrıca önleyici olmayan çoklu görev olarak da bilinir: "Önleyici olmayan Çoklu Görev" . PC Dergisi . Erişim tarihi: 15 Ağustos 2015 .
  6. ^ David Hoag (Eylül 1976). "Apollo Araç İçi Rehberlik, Navigasyon ve Kontrol Tarihi" (PDF) . Charles Stark Draper Laboratuvarı.
  7. ^ "New York Times Bulmaca Cevapları" . 13 Ekim 2013. bilgi işlem .. bir kusur .. hangi .. döngü
  8. ^ "Hesaplama Teorisinde Durma Problemi" . 3 Ekim 2018.
  9. ^ "DameWare Uzaktan Kontrol yazılımına Karşı Bir Arabellek Taşması Exploit" . 19 Aralık 2003. Komut kabuğu bir kontrol-c kombinasyonu ile kapatılır kapanmaz ...
  10. ^ Ada Programlama: Kontrol: Sonsuz Döngü
  11. ^ "C/C++'da sonsuz döngü" . 2016-08-03 tarihinde kaynağından arşivlendi .
  12. ^ Lee Dohm (24 Mayıs 2013). "Alderson döngüsü" .
  13. ^ "Alderson Döngüsü" . Jargon Dosyası , Sürüm 4.4.7 . 2006-05-15 tarihinde kaynağından arşivlendi . 2006-05-21 alındı .

Dış bağlantılar