İstisnalar bir OOP konsepti midir?


37

Dün bir yazıyı okuduktan sonra, istisnaların kaynağı hakkında fazla bir şey bilmediğimi fark ettim. OOP ile ilgili bir kavram mı sadece? Ben öyle düşünüyorum, ama yine de veritabanı istisnaları var.


Bir keresinde "Bay Goodenuf" un (ya da benzerlerinin) "boşver, bu Goodenuf, ha!" Cevabında istisnalar yarattığını okudum. stil zorbalık. Şimdi bir referans bulamıyorum - belki başka biri bulabilir. İlk önce hangi dile eklendiklerini bilmek ilginç olurdu.
Steve314

7
Haskell'in istisnaları var ve OOP değil
jozefg

1
İstisnaların kendileri kesinlikle nesne yönelimli olmasa da, istisnaları nesneler olarak tanımlama ve bu nesnelerin örneklerini atma ve yakalama ortak uygulama çok OOP'dir.
Dougvj

Bir istisna ve GOTO arasındaki fark nedir ilginç bir soru.
Austin Henley

2
@Austin - "İstisnalar, tek bir çıkış noktası ilkesini ihlal ettiği halde, yapılandırılmış programlama programlarının en katı uygulayıcılarının mutlak bir şekilde savunucu olmalarına rağmen, sınırsız spagetti kontrolünün olduğu gibi akmasına izin vermezler goto. Atma, blok yapıların yuvalanmasına dayanan bağlamla belirlenir. Bu nedenle, istisnalar, tek çıkış ilkesinin bir kılavuz olarak alındığı, ancak mutlak olmadığı, biraz daha az katı bir yapılandırılmış programlama biçimine dayanır ".
Steve314

Yanıtlar:


5

İstisnalar bir OOP konsepti değildir.

Ancak bunlar küçük bir noktada da tamamen ilgisiz değil.

Diğer cevapların göstermiş olduğu gibi: İstisnalar kavramı, bazı OOP dışı dillerde bunu yapmıştır. Bu kavramdaki hiçbir şey OOP'tan bir şey gerektirmez .

Ancak, OOP'yi alan tüm OOP dilleri ciddiye alınmazsa , istisnalar gerektirir, çünkü diğer hata işleme yöntemleri belirli bir noktada başarısız olur: Yapıcı.

OOP'nin noktalarından biri, bir nesnenin iç durumunu tamamen ve tutarlı bir şekilde kapsüllenmesi ve yönetmesidir. Bu, aynı zamanda, saf OOP'de "atomik olarak" tutarlı bir duruma sahip yeni bir nesne oluşturmak için bir konsepte ihtiyaç duyduğunuz anlamına gelir - bellek tahsisinden (gerekirse) başlangıç durumuna getirmeye, anlamlı bir duruma (yani hafızayı sıfırlamak yeterli değildir). bir ifadede yapılması. Dolayısıyla bir yapıcı gereklidir:

Foo myFoo = Foo("foo", "bar", 42);

Ancak bu, yapıcının bir hata nedeniyle de başarısız olabileceği anlamına gelir. İstisnalar olmadan hata bilgisini kurucudan nasıl yaymak?

  • Geri dönüş değeri? Bazı dillerde newsadece başarısız olabileceğinden, nullancak herhangi bir anlamlı bilgiden kaynaklanamadığı için başarısız . Diğer dillerde (örneğin, C ++) myFoobir işaretçi değildir. Buna karşı kontrol edemediniz null. Ayrıca myFoohata hakkında soru soramazsınız - başlatılmadı ve bu nedenle OOP düşüncesinde "yok".

  • Global hata bayrağı? Kapsülleme durumu ve ardından bazı global değişkenler hakkında çok fazla şey var mı? H gidin ... ;-)

  • Bir karışım? Hiçbir şekilde daha iyi değil.

  • ?

Bu nedenle istisnalar, OOP'tan daha temel bir kavramdır, ancak OOP, doğal bir şekilde üzerlerine dayanmaktadır.


3
Söyleyebileceğim kadarıyla, bu asıl soruyu ele alan bu “cevap” içindeki tek kelime “değil” dir. Bu ikisinin arasında okur bana saygısızlık - dinlenme OOP'deki istisnalar hakkında görünüyor belli belirsiz ilgili ve tamamen alakasız - Söz bağlamında tekrar sordu
tatarcık

@gnat: TO, istisnaların kökenini bilmediğini de söylüyor. Bu nedenle, OO ülkesinde istisnaların neden heryerde olduğunu gösteren küçük bir geçmiş benim için uygun görünüyordu. YMMV
AH,

1
@AH Açılış çizgisinin dışında gnat ile aynı fikirdeyim, bu gerçekten soruyu ele almıyor. Gnat'a cevabınız "istisnaların kökenleri hakkında bir şey bilmediğini söylüyor" oldu, ancak aslında istisnaların bir kökenini vermediniz, yalnızca nesne örneklemesi sırasında istisnaların bazı rasgele kullanımlarını vermediniz.

Çocuklar, cidden mi? -1? Diğer cevapların çoğu da% 100 değil. +1 benden telafi etmek için. Bu cevap, bozuk sınıf tasarımları dünyasında iyi bir öneri sunar. (Değişiklik: Çok adımlı inşaatçılardan kaçınılmalıdır)
Jo So

44

OOP sadece ilgili mi?

Hayır. İstisnalar ve OOP ilgisizdir.

İstisnaların ele alınması hataları ele almak için bir mekanizmadır. Bir istisna, mevcut yürütme durumunu önceden tanımlanmış bir yere kaydetmek ve yürütmeyi bir istisna işleyicisi olarak bilinen belirli bir alt rutine geçirmek suretiyle gerçekleştirilir.

C ( gerçekten OOP dili değil , bir şekilde C'deki istisnaları taklit etmek mümkün ) ve C ++ (OOP, istisnaları destekliyor) karşılaştırarak hiçbir şey C'nin standart komitesinin C'ye istisnalar eklemesini engellemiyor, yine de C'yi OOP dili yapmıyor.


2
Genel işletim sistemlerinde desteklenen bir takım istisnalar olduğunu bile iddia edebilirsiniz. Programınızın çökmesine (yakalanmamış "istisna") izin verin ve bir çekirdek dökümü ve hata ayıklayıcı ile yığın izlemesi bile elde edin.
bhaak

12
MS BASIC bile 80'lerin başlarında istisnai durumlara sahipti:ON ERROR GOTO xxxx
jwernerny

1
@bhaak Ayrıca Windows'ta Bellek dökümü hakkında da konuşuyor olabilir
JohnL

11
@jwernerny Hata işleme? Emin. Ancak hiç kimse bu istisna işlemesi demez. Aslında, rutin edildi tezat (yapılandırılmış) istisna işleme için.
Konrad Rudolph

1
@jwernerny izlediğimden emin değilim; Anladığım kadarıyla istisna işleme hata işleme yapmak için çok özel bir yoldur. İstisna duyduğumda her zaman try catchyapıyı düşünüyorum .
Andy

12

Bunun bir istisnası, basitçe, dikkat gerektiren ve çoğu zaman bir programın yürütme akışındaki değişiklik gerektiren istisnai bir durumdur. Bu tanım gereğince, istisnalar ve istisnaların ele alınması nesne yönelimi ile sınırlı değildir ve basit program hataları bir istisna biçimi olarak düşünülebilir.

Nesneye yönelik diller tipik olarak yerel bir istisna sınıfına sahiptir ve bağlama bağlı olarak, "istisna" kelimesi genel kavram yerine o ana sınıfa atıfta bulunabilir. Nesne yönelimli istisna işleme, çoğu nesne yönelimi olduğu gibi, sözdizimsel şekerdir ve kesin olarak nesne yönelimli olmayan dillerde kolayca taklit edilebilir. İşte C Programming wikibook'tan bir C örneği :

#include <stdio.h>
#include <setjmp.h>

jmp_buf test1;

void tryjump()
{
    longjmp(test1, 3);
}

int main (void)
{
    if (setjmp(test1)==0) {
        printf ("setjmp() returned 0.");
        tryjump();
    } else {
        printf ("setjmp returned from a longjmp function call.");
    }
}

6
Sadece sözdizimsel şeker değildir. Tam istif açma ve tür tabanlı yakalama işleyicilerinin yeniden oluşturulması setjmp ile zordur. Ek olarak, istisnaların uzmanlık derlemesi setjmp ile taklit edilemeyecek avantajlar sağlar.
edA-qa mort-ora-y

3
Tanımlama istisnalarının istisnai durumlardan nefret ediyorum. Bir hata durumunun mevcut bağlamla çözülemediği durumlarda istisnalar oluşturulması (istisnalar) yapılmasını tercih ederim çünkü mevcut bağlamda hatayı doğru bir şekilde düzeltmek için yeterli bilgi yok.
Martin York


9

Cevap basit bir NO.

İstisnaları olmayan OO olmayan bir dil için iyi bir örnek ADA'dır.


4
Hm, neden ADA bir OO dili değil? Verildiği gibi, ADA83 polimorfizminden yoksundu ancak yine de nesneye dayalı olarak değerlendirilebilir. Ayrıca ADA95'ten beri dil tamamen nesne yönelimlidir.
yannis

Bildiğim kadarıyla istisna işleme ADA83'ten daha eski, bu nedenle ADA, istisna işleme özelliğine sahip bir OO değil.
Uwe Plonus

2
@YannisRizos: Ada83'te paketler ve genel paketler var ancak nesneler yok. Ada95 ile tanıştırıldılar.
moouviciel

2
@Yannis - Polimorfizmi olmayan nesneler iç içe bloklar olmadan yapılandırılmış programlama gibidir. Polimorfizm, OOP'nin tanımlayıcı özelliklerinden biridir. Ada95'de bile, çalışma zamanı bağlamayı destekleyen türlere, elbette sadece yazım kurallarına rağmen "sınıflar" yerine "etiketli türler" denir. Ada 83'ün değişken kayıtları ve çeşitli diğer türleri vardı, ancak bu türlerin hiçbiri OOP'a özgü özellikler sunmuyor. Ada 83 modüler ve yapılandırılmış, ancak nesne yönelimli değildi.
Steve314,

3
@Yannis - Temel olarak, Ada topluluğundaki bazı insanlar (çoğu dilin bazı savunucuları gibi) bir özelliğin iyi olabileceğini, ancak en sevdikleri dilde uygulanamayacağını kabul edemez ve aksi takdirde inanmak için her türlü mazereti oluşturabilir. Yine de, iyi bir dilin olası tüm iyi dil özelliklerine sahip olması gerekmiyor bile (Ada tasarımcılarının öyle düşündüğüne inanmak kolaydır). Dil tasarımına minimalist bir yaklaşıma gerçekten inanmıyorum, ancak maksimalist diller de mükemmel değil.
Steve314

7

Zaten burada çok iyi cevaplar. İstisnaları olmayan OOP dışı programlama dilleri için diğer örnekler:

  • Oracle PL / SQL

  • Klasik Visual Basic (V6 ve altı, "On Error Goto" IMHO bir istisna işleme biçimidir)

(Nitty olmak: Her iki dilde de bazı OO unsurları buluyorsunuz, ancak istisna işleme mekaniği bunları kullanmıyor, sanırım kavram OO elemanlarının bu dillere eklenmesinden yıllar önce ortaya çıktığı için).


En azından DOS'taki QuickBASIC sürümleri (Visual Basic; QB 4.5, Wikipedia'ya göre 1988 idi, VB 1.0 1991'e göre) ON ERROR GOTOsözdizimi kullanarak hata işlemeye başladı . QuickBASIC'in bile OO'ya benzer birkaç kavramı vardı (bence QB 4.5 bazı sınıfları bile destekliyordu) ama çoğunlukla geleneksel BASIC'e uygun bir nesne yönelimli dil demeye zorlanıyordunuz. [Wikipedia ]
Ocak'ta

5

İstisnaların arkasındaki temel fikir, program akışını, programcının "normal" uygulama yolunu daha kolay takip edebilmesi için temizlemektir. Bir dosyayı C'da açmanın basit bir örneğini düşünün. Dosyayı açmaya çalıştıktan hemen sonra, programcının fopen () çağrısından gelen yanıtı incelemesi ve aramanın başarılı olup olmadığına karar vermesi gerekir. Eğer çağrı başarılı olmazsa, programcının uygun şekilde cevap vermesi gerekir. "Normal" yürütme yolundaki bir sonraki arama, belki de fread () veya fwrite () çağrısı, hata veya başarısızlık koşulları ele alındıktan sonra ortaya çıkar. Bir sonraki ekranda olabilir.

İstisnalar sağlayan bir dille, eşdeğer fopen () çağrısını fread () veya fwrite () ile hemen takip edebilirsiniz. "Normal" yürütme yolunun "sonraki adımı" nı gizleyen bir hata işleme yoktur. Programcı, normal yoldan daha fazlasını tek bir ekranda görebilir ve bu sayede yürütmeyi daha kolay takip edebilir. Hata işleme, programın başka bir bölümüne taşınır.

İstisnaların kendileri bir OOP konsepti değildir, ancak genellikle onları daha rahat ve güçlü kılan OOP konseptleri kullanılarak uygulanırlar. Örneğin, istisnalar bir kalıtım hiyerarşisinde tanımlanabilir. Bir dosyayı açmak ve okumak ya da yazmak konusundaki kavramsal örneğimizi kullanarak, bu çağrıların her biri çeşitli istisnalar oluşturabilir - FileClosedException, DeviceFullException, NoSuchFileException, InsicientFilePermissionsException, vb. GenericException kaynağından devralır.

Programcı bir konsepti test etmek için hızlı ve kirli bir uygulama yapıyorsa, istisnaların kullanılmasını çoğunlukla görmezden gelebilir ve GenericException için tek bir işleyici uygulayabilir. Bu işleyici, bir GenericException'ı ve GenericException'dan devralan herhangi bir istisnayı ele alır. Dosyayla ilgili herhangi bir istisnayı aynı şekilde ele almak isterse, FileException için bir işleyici yazabilir. Bu, FileExceptions ve FileException'dan miras kalan istisnalar için çağrılır. Farklı hata koşullarına farklı cevap verecek bir program yazmak istiyorsa, her özel istisna için belirli bir işleyici yazabilir.


3

Diğerleri de “Hayır” ı dil örnekleri ile doğru olarak cevapladılar Herhangi bir OOP içermeyen bir dile istisnalar eklemek için bir örnek ekleyerek uzayabileceğimi düşündüm.

Ben DSKL (Bildirimsel Sıralı Çekirdek Dili) durumunda bu yapacak OZ , iyi böyle akademi şeyler için uygun bir dilde. DSKL (veya DKL) burada (rastgele arama sonucu), Tablolar ve Değerler bölümünü görebilir. Kesin tanım, değiştirilemez değişkenleri olmayan (ilan edilmiş ve sonradan bağlanmış) ve yerleşik bir OOP içermeyen çok basit bir dil olması dışında önemli değildir.

OOP, bu çekirdek diline dilsel bir soyutlama olarak bile eklenemez. Çekirdek diline benzersiz adlar ekleyerek (NewName) ve yerel kapsamı kullanarak kapsülleme elde edilebilir. Veya çekirdek diline (NewCell) değişken bir durum ekleyerek ve yerel kapsama kullanarak kapsülleme ile uygun OOP elde edilebilir. Ama olamaz yalnız belirtilen çekirdek dili ile sağlanabilir.

O zaman çekirdek diline istisnalar eklersek, OOP desteği olmayan ancak istisnalar dışında bir dile sahip oluruz. Nasıl olduğunu göstereyim:

Bir yığın ve depolama ile soyut bir makine tanımlayarak, dilimizdeki her bir ifadenin ne yapması gerektiğini tanımlayabiliriz ( deyimin anlamını ). Örneğin skip, yığında hiçbir şey yapmamalı A = 3, yığında ise (/ birleştirmek) A'dan (/ ile) 3'e kadar bağlanmalıdır.

İstisnalarımızın nasıl tanımlanması gerektiğinin sözdizimini ekleyerek başlarız . Bunu <statement>DKL’ye iki cümle daha ekleyerek yapıyoruz .

<statement>  ::== ... (old stuff)
                 | try <statement> catch <id> then <statement> end
                 | raise <id> end

İşte bilinen deneme / yakalama ve istisnaları artırmanın / atmanın bir yolu.

Anlambiliklerini soyut makinede nasıl çalışması gerektiği ile tanımlıyoruz :


Anlamsal deyimi deneyin : (try <statement1> catch <id> then <statement2> end)
Yap:

  1. Semantik deyimi yığına itin (catch <id> then <statement2> end)
  2. Semantik deyimi yığına itin (<statement1>)

1. ifadenin yığının üstünde olacağını ve önce çalıştırılmayı denediğini unutmayın.


Anlamsal ifade: Yükselt(raise <id> end)
:

  1. Yığında başka bir şey yoksa, durdurulan ve yakalanmamış bir istisnayı rapor edin.
  2. Aksi halde, ilk anlamsal deyimi yığından patlat. Bu bir catch ifadesi değilse, 1. adıma gidin.
  3. Yığın üzerine (catch <id> then <statement> end)
    basma formunda bir yakaladık (<statement>).

Yakalama
Normal uygulama sırasında bir yakalama ifadesi görürsek, bu, içeriye ne olursa olsun, bu seviyeye kadar istisnalar olmadan yürütülen anlamına gelir. Böylece sadece catchyığını açıp hiçbir şey yapmıyoruz.

QED, istisnalar dışında bir dilimiz var ve OOP olasılığımız yok.

Daha basit hale getirmek için ortam kısmını soyut makineden çıkardım.


1

Yok hayır.

IIRC, ilk OO dilinden önce istisnalar ortaya çıktı. AFAIK, istisnalar ilk önce LISP uygulamalarıyla desteklendi. Erken yapılandırılmış diller (örneğin ALGOL) ve erken OO dilleri (örneğin SIMULA) istisnaları desteklemiyordu.


Elbette, ALGON 68 istisnalar da ("olaylar") vardı, ama bunun dışında her şey vardı. PL / Onlara ("ON koşulları") da sahiptim ve 1969'dan bunların kullanımlarını anlatan literatür var.
Ross Patterson
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.