SORU
22 AĞUSTOS 2013, PERŞEMBE


Hiç çalıştırılacak olan kod tanımsız davranış çağırabilirsiniz?

Tanımsız davranış (örneğin, sıfıra bölme) çağıran kod asla idam alacak, program hala tanımsız davranıştır?

int main(void)
{
    int i;
    if(0)
    {
        i = 1/0;
    }
    return 0;
}

Hala tanımsız davranış olduğunu düşünüyorum, ama ya bana destek verme konusundaki standart herhangi bir kanıt bulamıyorum.

Yani, herhangi bir fikir?

CEVAP
22 AĞUSTOS 2013, PERŞEMBE


C standart tanımlar nasıl bakalım "davranış" ve "tanımsız davranış".

Başvuru için N1570 taslak ISO C standard 2011; bilgim yok konuyla ilgili farklar her üç yayınlanan ISO C standardı (1990, 1999, 2011).

Bölüm 3.4:

davranış
dış görünüş ya da eylem

Tamam, bu biraz belirsiz, ama belirli bir açıklama yok olduğunu iddia ediyorum "" Kesinlikle hayır "eylemi aslında idam olmadığı sürece.", görünümünü

Bölüm 3.4.3:

tanımsız davranış
hatalı veri, nonportable ya da hatalı bir program kullanımı üzerine inşa veya davranış bu Uluslararası Standart gereksinimlerini etkiler

Diyor "kullanımı üzerine" de böyle bir kavram. Kelime "" biz sonbaharda çok standart tarafından tanımlanan, yaygın değildir İngilizce anlamı. geri kullanın İnşa "kullanıldığında ise" asla idam değil. bir

Bu tanım altında bir not var:

Durumu görmezden gelmek Mümkün tanımsız davranış NOT aralıkları tamamen öngörülemeyen sonuçları ile, Çeviri sırasında davranıyor veya belgelenmiş bir şekilde karakteristik programı yürütme ortam (ya da tanısal bir mesaj verilmesi olmadan) çeviri işine son vermek veya yürütme (a verilmesi ile tanı iletisi).

Bir derleyici programınızı reddetmek için izin verilirderleme zamanındaeğer davranışı tanımsızdır. Ama benim yorumum busadeceprogramın her yürütme tanımsız davranış karşılaşacak kanıtlar. Sanırım, bu anlamına gelir:

if (rand() % 2 == 0) {
    i = i / 0;
}

hangi kesinlikleolabilirtanımsız davranış var, derleme zamanında reddetti.

Pratik bir mesele olarak, program çalışma zamanı testleri yapabilen tanımsız davranış yürütmesini karşı korumak için olmak zorunda, ve standart onlara bunu yapmak için izin vermek için vardır.

Örnek:

if (0) {
    i = 1/0;
}

asla 0'a bölümü yürütür. Çok yaygın bir deyim vardır:

int x, y;
/* set values for x and y */
if (y != 0) {
    x = x / y;
}

Bölümü kesinlikle y == 0, ama asla y == 0 eğer idam olursa tanımsız davranış var. Çünkü bu davranış, iyi tanımlanmış ve örnek, iyi tanımlanmış aynı sebepten: ^em>potansiyeltanımsız davranış aslında hiç olmaz.

(INT_MIN < -INT_MAX && x == INT_MIN && y == -1 (Evet, tamsayı bölme taşması olabilir) tabii, ama o ayrı bir mesele.)

Yorum (beri silinmiş), biri derleyici derleme zamanında sabit ifade değerlendirmek olabilir dikkat çekti. Bu bağlamda, çünkü bu durumda doğru, ama konuyla ilgili değil

i = 1/0;

1/0sabit bir ifade değil.

Birconstant-expressionazaltan sözdizimsel bir kategoridirkoşullu-ifadeatamaları ve virgül ifadeleri hariç). Üretimconstant-expressiondilbilgisi görünürsadeceaslında sabit bir ifade, dava etiketleri gibi gerektiren ortamlarda. Eğer yazarsan:

switch (...) {
    case 1/0:
    ...
}

sonra 1/0 6 kısıtlamayı ihlal eden sabit bir ifade ve bir.6p4: "Her sabit ifadesi gösterilebilir aralığında olan sabit için değerlendirecektir kendi türü için", değerler. bir tanı gereklidir. Ama bir atamanın sağ tarafında bir gerektirmezconstant-expressionsadece birkoşullu-ifade, geçerli değil sabit ifade. kısıtlamalar çok Bir derleyici değerlendirilmesi, herhangi bir ifade bu mümkün için derleme zamanında, ama yalnızca bir davranıştır aynı olarak değerlendirilmiş sırasında yürütme (ya da, bağlamında if (0),değilyürütme sırasında değerlendirilir().

(Tam olarak görünen bir şey gibiconstant-expressionolması şart değilconstant-expressionsadece olarak, x y * z dizi x y bir değilkatkı maddesi ifadegöründüğü içerik yüzünden.)

Alıntı gittiğini N1570 bölüm 6.6: Dipnot anlamına gelir

Böylece, aşağıdaki başlatma
static int i = 2 || 1 / 0;
ifade değeri geçerli bir tamsayı sabit ifadesidir.

bu soruya aslında ilgili değil.

Son olarak, olmayan tanımsız davranış yürütme sırasında neler hakkında neden tanımlanan birkaç şey var. Ek-J, C standardı (yine N1570 draft) bölüm 2 tanımsız davranışlara neden olan şeyler listeleri, standart geri kalanından bir araya geldiler. Bazı örnekler (bu ayrıntılı bir liste olduğunu iddia etmiyorum)

  • Boş olmayan bir kaynak dosyası hemen ters eğik çizgi karakteri veya kısmi biter değil öncesinde yeni satır karakteri bitmiyor önişleme token veya yorum
  • Token birleştirme karakter dizisi evrensel karakter adı sözdizimi eşleşen üretir
  • Karakter kümesi kaynak dosyada karşılaşılan temel kaynağı, bir tanımlayıcı dışında değil, bir karakter, bir karakter sabiti, bir dize üstbilgi adı, bir yorum değişmez, ya da bir ön belirteci hiç bir simge haline getirilmiştir
  • Tanımlayıcı, yorum, dize, karakter sabiti, ya da başlık kısaltması adı geçersiz bir karakter içeriyor veya başlamıyor ve ilk vardiya durumu ile bitiyor
  • Aynı tanımlayıcı çeviri aynı birim içinde hem iç hem de dış bağlantı vardır

Bu belirli durumlarda bir derleyici şeylerolabilirAlgıla. Onların davranış Komitesi istemedi, ya da değil, tüm uygulamaları aynı davranışı empoze edemez, çünkü tanımsız olduğunu düşünüyorum, ve izin verilen davranışların sadece bir dizi tanımlama çabaya değer değildi. Gerçekten "hiç", ama ben burada söz bütünlüğü için çalıştırılacak kod kategoriye girer yok

Bunu Paylaş:
  • Google+
  • E-Posta
Etiketler:
C

YORUMLAR

SPONSOR VİDEO

Rastgele Yazarlar

  • cdgotx

    cdgotx

    8 Kasım 2011
  • The Verge

    The Verge

    8 AĞUSTOS 2006
  • Tylerron

    Tylerron

    6 AĞUSTOS 2006