2016-03-29 26 views
0

Aşağıdaki kodu yazdım (Sadece anlama amacına yöneliktir). Ana dışında, int b; geçici tanım anlamına gelir. İç ana int b = 16 yerel bir değişkendir. Fonksiyon değişkeninin içinde b dahili bağlantıya sahiptir (dosya kapsamı). Çıktı 16 ve 0'dır. Hafızanın, yalnızca başlatıldıklarında geçici olarak tanımlanmış değişkenler için tahsis edildiğini okudum. İşte buradaki sorum, fonksiyonun içinde, printf b'nin değerini basar ve printf çağrıldığında bellek ayrılır mı? Öyleyse, belleğe, ilk erişildiklerinde (başlatılmış veya erişilmiş olsun) geçici olarak tanımlanmış değişkenlere tahsis edildiğini söyleyebilir miyim? Yoksa yanılıyor muyum? daha netlik ekleme: DüzenlendiGeçici Tanım ve bellek ayırma

int b; 
int b; 
void f1(int a1); 
int main() 
{ 
    int b=16; 
    printf("b=%d\n",b); 
    f1(5); 
    return 0; 
} 

void f1(int a1) 
{ 
    printf("b = %d\n",b); 
} 

ben işlevi içinde değişken ana o farklı olduğunu farkındayım. Ayrıca yerel değişkenin yığın halinde olduğunun farkında olun. Benim sorumum, geçici tanım ile ilgilidir. int b iki kere deklare edildi ve C cinsinden kabul edildi çünkü kesin bir tanımdır. Gerçek tanımı olması durumunda, birden fazla tanımlamaya izin verilmez ve dolayısıyla bu kabul edilmez. Geçici tanım hakkında birkaç soru vardır (About Tentative definition). Bunlardan birine göre, "C, hepsi aynı ve eşleştiği sürece aynı değişken için birden fazla tanımlamaya izin veren özel" geçici bir tanım "kuralıdır. C derleyicisi, sahnelerin ardında tüm geçici ifadeleri birleştirir. tek bir tanım olarak tanımlar. " Sorularımı yeniden ifade etmek için:

Değişken sadece geçici olarak tanımlanmış, ancak kullanılmıyorsa bellek ayrılıyor mu? (derleyicinin kodu optimize etmediği varsayılarak). Çeviri biriminin sonunda göründüğü gibi, bellek yukarıda belirtilen soruya göre tahsis edilir. Ya da bellek sadece yumruk zamanı için kullanıldığında (bu durumda printf deyiminde) atanır mı?

+0

'int b; int b; 'izinli? : O – Downvoter

+0

* "Çevirme biriminin sonuna ulaşılmışsa ve tanımlayıcı için bir başlatıcıda hiçbir tanım görünmediyse, geçici bir tanım tam tanım haline gelir" *.Bu yüzden son geçici tanım, global kapsam ve sıfır olarak başlatılmış bir gerçek haline geliyor. –

+0

@cad: Aynı oldukları için: evet. Örneğin; 'typedef int; Bu b; ', standarda bakmak zorunda kaldı, ama yine de cehennem gibi bunu önlemek istiyorum. – Olaf

cevap

0

Bunlar iki farklı değişkendir.

Genel int b; için, program belleğe ilk yüklendiğinde bellek ayrılır. Programın genel belleğinde bulunur ve programdaki herhangi bir noktadan kolayca erişilebilir.

main()'in yerel int b=16; için yığında main() işlev çerçevesinde ayrılmıştır. Bu işleve yalnızca doğrudan bu işlevden erişilebilir. Başka bir şey, main() değişkenleri adresinin veya yığındaki bazı karmaşık işaretçi aritmetiğinin iletilmesini gerektirir.

yerel bgizler aynı ada sahip, dolayısıyla bu işlevinden küresel birini kullanamazsınız çünkü küresel b

(bazı diller buna izin C değil), fakat o kadar. Bunlar farklı değişkenlerdir ve adı değiştirdiyseniz programınızın ikili (yani çalıştırılan gerçek talimatlar) değişmeyecektir.

0

int b;'un neden sıfırlandığını açıklayan bu cevaba bakın. Bu standart söylüyor çünkü

Does gcc automatically initialize static variables to zero?

ana içinde int b; yığını üzerinde ve fonksiyonu f1 kapsamında olan tek b sembolü olarak 16'e ayarlanmış Dosya kapsamında beyan edilen biridir ve sıfır başlatıldı oluyor olmalı.

İlgili konular