PDA

Tam Sürümünü Görmek İçin : c-header file


dreamer1983
22/05/2007, 16:10
(http://forum.donanimhaber.com/m_14442001/tm.htm#)Merhaba Arkadaslar,

1.h dosyasını header.c dosyama include edip aşağıdaki şekilde fonksiyon call yaptığımda fonkiyonları kullanabiliyorum(TreeFunction,TwoFunction). Fakat değişkenleri kullanamıyorum(2.h veya 3.h ta tanımlı c,d,e,f degikenleri).
"header.c" "1.h" yi include ediyor, "1.c" "2.h" yi include ediyor ve 2.c deki TwoFunction() fonsiyonunu çağırabiliyorum(2.h de TwoFunction() declerationı bulunuyor).
"header.c" "1.h" yi include ediyor, "1.c" "2.h" yi include ediyor,"2.c" "3.h" yi include ediyor ve 3.c deki TreeFunction() fonsiyonunu çağırabiliyorum.(3.h de TreeFunction() declerationı bulunmuyor).

İlişkiyi tam olarak çözemedim bir fikri olan arkadaşlar var ise sevinirim.

header.c
#include "stdio.h"
#include "1.h"


int main()
{
//d=TreeFunction(); //HATA
//d=5;//HATA
//g=5;//HATA
TreeFunction();
TwoFunction();
return 1;
}
****************** |
1.c
#include "2.h"
int OneFunction()
{
return 22;
}
--------------------------|
1.h
int OneFunction();
int a;
int b;

****************** |
2.c
#include "stdio.h"
#include "3.h"
int g;
int TwoFunction()
{
return 22;
}
--------------------------|
2.h
int TwoFunction();
int c;
int d;

****************** |
3.c
#include "stdio.h"
int TreeFunction()
{
return 33;
}
--------------------------|
3.h
int e;
int f;
****************** |


mr_c
22/05/2007, 18:59
bir yerlerde extern unutmuş olabilirmisin? Fonksiyonarın nerelerde ne şekilde tanımlayacağına da biraz göz gezdirmekte fayda var.

golgepapaz
22/05/2007, 19:46
sorun su ki,sen main fonksiyonunda sadece 1.h yi #include etmissin.o yuzden sadece o dosyada deklare edilmis degiskenleri kullanabilirsin. 1.c'nin 2.h yi include etmesi, header.c nin de 2.h yi gorecegi anlamina gelmez(zaten bunu istemezsin emin ol).Normalde treeFunction ve twofunction a da hata vermesi lazim,(en azindan c++ da.c de hata vermiyorsa olayi linker'in bulacagini dusunuyordur) eger 2.h ve 3.h de tanimlanan degiskenleri kullanmak istiyorsan, ya header.c de yada 1.h nin icinde onlari include etmen gerekiyor(2.h ve 3.h yi)

Revne
22/05/2007, 20:08
Dosyalar arasındaki carpık ilişkilerden kacınmak lazım.

Fonksiyon prototiplerini ve C dosyalarındaki degiskenleri Extern olarak bir H dosyasında toplaman daha yakışıklı olur...

Programın boyutu artıkça bu dosya 2 taneye cıkarılabilir. Aksi halde kimin eli kimin cebinde ugrasıp durursun..

#ifdef .....
Normal değişkenler
Extern degişkenler
Fonksiyonlar
#endif

Kolay Gelsin.

dreamer1983
22/05/2007, 23:05
Merhaba Arkadaşlar,
Teşekkürler ilginiz için öncelikle,
Aslında karmaşık ilişkilerden kaçınılabilir ama olayı çözebilmek için öyle küçük bir kod dizisi hazırladım. Yine extern ile değişkenler globalleştirilebilir fakat, fonksiyonda hata vermiyor, değişkende niye hata veriyor ki :garip:
Dikkat çekeceğim bir diğer nokta ben hiç bir yerde tanımlı olmayan bir fonkiyon call ettim XFunction(); diye, ve bunu
VC++ 6.0 da compile ettigimde hata vermiyor sadece şu şekilde bir warning veriyor "assuming extern returning int"
Yani TreeFunction() kullanımı aslında yanlış bir kullanım ama VC++ 6.0 derlerken extern olabilecegini dusunuyor obje dosyalarını link ederken ise TreeFunction() fonksiyonunu 3.o objesinden bulup yerine koyuyor, yani biraz artificial davranıyor galiba :).
Extern tanımlayarak değişkenler gördürülebilir, fakat fonksiyonlardaki benzer durumu değişkenlere niye uygulamıyor VC++ 6.0 onu anlayamadım doğrusu.
Biraz derleyici bagımlı bir konu gibi geldi problem bana ek olarak.

quasimodo
23/05/2007, 13:14
Fonksiyonlarda extern kullanmasanda hata vermiyor
cunku derleyici derleyecegi kodda bir fonksiyonla
karsilastiginda burayi bos birakir ve ilgili fonksiyona
gidilecegini bildiren bir isaret birakir cunku derleyici
bu fonksiyonun nerede oldugunu bilmez ama baglayici
bilir. Bu yuzden fonksiyonlar default olarak
extern dir ve dosya faaliyet alanina sahiptir.

Ama global degiskenlerde durum farklidir. Bu
degiskenlerin basina extern keyword unu getirmezsen
kullanimini sadece tanimli bulundugu modul icine kisitlamis
olursun . Aslinda sen global bir degiskeni extern
tanimlamakla derleyiciye
"Bu degiskeni baglama asamasinda ele al"
demis olursun.

acehreli
23/05/2007, 15:48
dreamer1983, "bildirme" (declare) ile "tanimlama"nin (define) farkini hatirlamakta yarar var:


// islev (function) bildirimi:
double foo(int);

// islev tanimi:
double foo(int i)
{
return 1.1 + i;
}

// nesne bildirimi VE tanimi:
BirTur birNesne;

// nesne bildirimi:
extern BirTur birNesne;


Yani sen XFunction diye bir islevin "hicbir yerde tanimli" olmadigini soylerken aslinda "kullanildigi noktada (senin 'call ettim' dedigin) ne oldugu bilinmeyen" demek istiyorsun.

C++'ta ve yeni C'de aslinda bu yasal degildir. Ama C'den kalma antika bir kural geregi, ne oldugu bilinmeyen islevlerin "int dOndUren ve belirsiz sayida parametre aldiklari" varsayilirdi. Derleyici bunu sana "assuming extern returning int" diyerek hatirlatiyor.

Eger derleyici uyari ayarlariyla oynayarak bu antika kurali engellersen, karisiklik azalacak.

Ali

dreamer1983
25/05/2007, 12:40
İlginiz için teşekkürler arkadaşlar.