İnt x {y = 5} neden mümkün?


10
int main() {
    int y;
    int x{ y = 5 };
    //x is 5
}

Bu nasıl mümkündür, çünkü y = 5 hesaplanabilir bir ifade değildir?

Ayrıca, neden derleyici veya IDE bir int döndürmüyor main () şikayet etmiyor?


8
y = 5 olan bir ekspresyon ve değere sahiptir 5. Neden olmadığını düşünüyorsun?
Yararsız

2
Eksik getirmedi returnarasında main, bakınız bu soruyu .
ceviz

3
Daha da iyisi, ikinci soruyu kaldırın. Bir tek soru başına soru Yığın taşması tercih modelidir.
StoryTeller - Unlander Monica

Belki de y = 5burada neden 5 verimi olduğu sorusunu yeniden tanımlamalısınız . Atama işleçlerinin bir şey döndürme olasılığı gerçekten de C / C ++ 'nın tuhaf bir özelliğidir.
user7860670

Yanıtlar:


11

Son sorunuzdan başlayacağım

Ayrıca, neden derleyici veya IDE bir int döndürmüyor main () şikayet etmiyor?

C ++ Standardına göre (6.6.1 ana işlevi)

5 Bir return deyimi, ana işlevi terk etme (otomatik depolama süresi olan herhangi bir nesneyi yok etme) ve argüman olarak dönüş değeri ile std :: exit öğesini çağırma etkisine sahiptir. Kontrol, ana bileşiğin ifadesinin sonundan akarsa, etki 0 işlenenli bir dönüşe eşdeğerdir (ayrıca bkz. 18.3).

Ve bu soruya göre

Bu nasıl mümkündür, çünkü y = 5 hesaplanabilir bir ifade değildir?

C ++ Standardından (8.18 Atama ve bileşik atama işleçleri)

1 Atama operatörü (=) ve bileşik atama operatörleri sağdan sola gruplandırılır. Hepsi sol işlenen olarak değiştirilebilir bir değer gerektirir ve sol işlenene referansla bir değer döndürür.

Sp bu beyan

int x{ y = 5 };

eşdeğer olarak iki ifadeye bölünebilir

y = 5;
int x{ y };

Dahası C ++ 'da y değişkenine aşağıdaki şekilde bir referans bile yapabilirsiniz

int &x{ y = 5 };

İşte örnek bir program

#include <iostream>

int main() 
{
    int y;
    int &x{ y = 5 };    

    std::cout << "y = " << y << '\n';

    x = 10;

    std::cout << "y = " << y << '\n';
}

Çıkışı

y = 5
y = 10

Bu beyanı yapabilirsiniz

int x{ y = 5 };

ayrıca yeniden yaz

int x = { y = 5 };

Bununla birlikte, iki beyan arasında (yukarıdaki beyanlara benzer şekilde) iki fark arasında bir fark olduğunu dikkate alın.

auto x{ y = 5 };

ve

auto x = { y = 5 };

İlk bildirimde değişkenin xtipi vardır int. İkinci bildirimde değişkenin xtipi vardır std::initializer_list<int>.

Farkı daha görünür hale getirmek için, nesnelerin değerlerinin nasıl çıktılandığını görün.

#include <iostream>

int main() 
{
    int y;
    auto x1 { y = 5 };  

    std::cout << "x1 = " << x1 << '\n';

    auto x2 = { y = 10 };   

    std::cout << "*x2.begin()= " << *x2.begin() << '\n';

    std::cout << "y = " << y << '\n';

    return 0;
}

Program çıktısı

x1 = 5
*x2.begin()= 10
y = 10

16

Bu nasıl mümkündür, çünkü y = 5 hesaplanabilir bir ifade değildir?

Bir ödevdir ve ödevler değer verir, yani "sol işlenenin cv-niteliksiz türü", bkz. [Expr.ass / 3] . Bu nedenle y = 5sonuçlanan yolan 5başlatmak için kullanılan, x.

İkinci sorunuzla ilgili olarak, ana sayfada (veya [basic.start.main / 5] ) cppreference'a bakın :

Ana işlevin gövdesinin returnifadeyi içermesi gerekmez : denetim, bir returnifadeyle karşılaşmadan ana sonuna ulaşırsa , etki yürütmektir return 0;.

Bu nedenle, derleyicinin veya IDE'nin returnsonunda eksik bir ifade hakkında sizi uyarması çok mainyanlış olur. Kuşkusuz, her zaman işlev dışı yürütmedenreturn itiraz etmeniz gerektiği gerçeği, sanırım ... tarihsel nedenlerden ötürü.voidmain


2
Bir ifade bir değerle sonuçlanabilir , ancak yalnızca bir işlev bir değerle sonuçlanabilirreturn . -pedantik
Yararsız

Bence bu int x {y = 5}; Açıklama c
bhura

@bhura - soru C değil C ++ ile ilgili
StoryTeller - Unslander Monica

Belki de gerekli olmasa bile, yine de ana değerden dönmenin genellikle iyi bir uygulama olarak kabul edildiğini belirtmek gerekir.
Aconcagua

4

operator=()Değişkene atanan değer olan bir değer, ile sonuçlanır. Bu nedenle, böyle atamaları zincirlemek mümkündür:

int x, y, z;
x = y = z = 1;

Atama ifadesi bir sahiptir değeri . İşlevlerin dönüş değerleri vardır; ifadeler değil.
Pete Becker

3

Cppreference ile ilgili belgelere bakarsanız operator=(), atanan nesneye bir başvuru döndürdüğünü görürsünüz . Bu nedenle, bir atama, atanan nesneyi döndüren bir ifade olarak kullanılabilir.

Sonra, bu sadece parantez ile normal bir ödev.

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.