Kayıt Ol

Giriş

Şifremi Kaybettim

Lost your password? Please enter your email address. You will receive a link and will create a new password via email.

soru ekleme

Soru sormak için giriş yapmalısınız.

Giriş

Kayıt Ol

.........

C KARAKTERLER ve KARAKTER DİZİLERİ

C KARAKTERLER ve KARAKTER DİZİLERİ

KARAKTERLER

C’de tanımlı bulunan char veri tipi sayesinde karakter değerlerimizi hafıza da saklayabiliyor ve onları işlemlere tabi tutabiliyorduk.

char veri tipinde tanımlanmış değişkenler için hafızada 1 byte lık yer ayrılır. Char veri tipi içerisinde a-z arası küçük harfler, A-Z arası büyük harfler, 0-9 arası rakamlar, noktalama işaretleri ve özel karakterler (, . : ; ! ? ( ) [ ] { } ….) saklanabilir. Karakter tipindeki bir değer hafızada o karaktere karşılık gelen ASCII kod karşılığı bir sayı olarak saklanırlar. Yani esasında hafızada saklanmış bir karakter aslında bir sayıya karşılık gelir. Bu sebepten dolayı char tanımlanmış bir değişken, içinde –128 ve 127 arası bir sayıyı da saklayabilir. Bu bir hata oluşturmaz.

Karakter değerler değişkene aktarılırken ‘ ’ (Tek tırnak ) işaretleri arasında aktarılırlar ve karakterler üzerinde matematiksel işlemler yapılamaz.

char krktr; şeklinde tanımlanmış bir değişkene içerisine aşağıda görülen şekillerde atama yapılabilir:

krktr = ‘a’;

krktr = ‘A’;

krktr = ‘5’; /* 5 bir sayı değil karakterdir. Matematiksel işlemlerde kulllanılamaz.*/

krktr = ‘!’;

krktr = 35; /* 35 sayısı saklandığı için tırnak koyulmadı. Bu sayı matematiksel işlemlerde kullanılabilir.*/

char veri tipindeki bir değişken scanf ( ) ve printf ( )konutlarında %c formatı ile okutulur ya da yazdırılır.

KARAKTER DİZİLERİ (DİZGİLER-STRİNGS)

C dilinde, yanyana gelmiş birden fazla karakteri (mesela bir isim bilgisini) saklayabilmek için ayrı bir veri tipi bulunmaz. Biz yanyana gelmiş birden fazla karakteri saklamak için iki yöntem uygularız:

  • KARAKTER DİZİLERİNDEN FAYDALANIRIZ: Karakter grubundan oluşan bir değişkeni ancak içinde karakter saklayabilecek bir dizi tanımlayarak kullanabiliriz.

Genel tanımlama kuralı: char dizgi_değişkenin_ismi[boyut];

char  renk [10];           şeklinde bir tanımlama renk isminde, içerisinde en fazla 10 karakter saklayabilecek bir dizgi değişkeni ifade eder.

Bu şekilde tanımlanmış bir dizgi içerisine değer aktarma sadece aşağıda söyelenen şekillerde yapılabilir:

  1. Tanımlama esnasında: char renk [10] = “mavi”;

Bu durumda   renk [0] = ‘m’;

                        renk [1] = ‘a’;

                        renk [2] = ‘v’;

renk [3] = ‘i’;             değerlerini alacaktır. Bu sebeple diziye ilk değer atama işlemini hatırlarsak aynı atama işlemi şu şekilde de yapılabilirdi:

char renk = {‘m’, ‘a’, ‘v’, ‘i’};

Burada dikkat edilmesi gereken en önemli nokta eğer dizgi karakter dizisi şeklinde tanımlanmışsa atanacak değer sadece tanımlama esnasında atanabilir. Programın herhangi bir yerinde sonradan değer ataması yapılamaz. Sonradan değer atamak ya da değiştirmek ancak strcpy( ) hazır fonksiyonu ile yapılabilir. (Karakter dizisi olarak tanımlanmışsa bu kural geçerlidir. Gösterici (pointer) olarak tanımlanmışsa istenen her zaman “ ” (çift tırnak) ile atama yapılabilir.)                     

  1. scanf ( ) fonksiyonu ile klavyeden okutarak: Karakter dizisi şeklinde tanımlanmış bir dizgi içerisine klavyeden değer okutulabilir. Burada dikkat edilmesi gereken nokta kullanılacak formatın %c değil %s olmasıdır. Çünkü girilen tek bir karakter değil bir karakter grubudur. Scanf ile dizgilere değer okutulurken diğer değişken isimleri önüne konan & (adres) operatörü dizgi adı önüne konmaz. Çünkü hatırlarsak dizi isimleri zaten bir adresi, (dizginin ilk elemanının adresini) ifade ederler. Dizgi de bir karakter dizisi değil midir? Aşağıdaki scanf ( ) kullanımını inceleyiniz.

scanf (“%s”, renk ); /*Dizgi okuma ve yazma formatı %s dir. Okuma işleminde aders operatörü (&) kullanılmamamlıdır. Dizgi adı bir dizi olduğundan zaten adres ifade eder.*/ 

  • GÖSTERİCİLERDEN FAYDALANIRIZ : Karakter gruplarını (dizgileri), karakter tipinde tanımladığımız bir gösterici içerisinde de saklayabiliriz. Böyle tanımlama yapmanın avantajı karakter sınırlaması olmaması ve istediğimiz her an içerisine değerini aktarabilmektir. Yani gösterici olarak tanımladığımızda değerini atama esnasında vermek ya da scanf ile okutmak zorunda kalmayız. İstediğimiz her an değer atayabiliriz.

char * renk;

renk = “mavi”;

scanf (“%s”, renk);

Göstericiler (pointer) ve diziler için geçerli  olan kurallar dizgiler için de geçerlidir. İsimlerinde ilk elemanın adresi saklıdır. İndis numarası vererek her bir elemana tek tek ulaşılabilir. İlk elemanın adresi artırılarak sonraki elemanlara ulaşılabilir.

printf (“renk = %s”, renk);                /*  renk = mavi */

            printf (“renk = %s” , &renk[0] );     /* renk = mavi */

            printf (“renk = %c”, renk [0] );        /* renk = m */

NOT: Örnek kodlarda da dikkat edebileceğiniz gibi tek bir karakter değişkene atanırken tek tırnak kullanılırken, bir dizgi yni karakter grubu atamasında çift tırnak kullanılır. Böylece biz değerin karakter mi yoksa bir dizgi mi olduğunu anlayabiliriz. Çünkü ikisinin hafızada saklanış yöntemi farklıdır.

c =  ‘A’;  /* Bir karakterdir. Hafızada A harfinin ASCII kod karşılığı olan 65 olarak saklanır.1 byte yer kaplar. */

c = “A” ; /* Bir dizgidir. Hafızada 2 byte yer kaplar. Sebebi için lütfen aşağıdaki konuyu inceleyiniz. */

DİZGİLERİN HAFIZADA SAKLANMASI

Karakter dizilerinin hafızada saklanması ile tek bir karakterin hafızada saklanması arasında önemli bir fark vardır.

  • Karakterler hafızada ilgili karakterin ASCII kod karşılığı olarak yani bir tamsayı olarak saklanırlar ve 1 byte yer kaplarlar.
  • Dizgilerin en son karakteri daima dizgi sonunu ifade eden NULL ya da ‘ \0 ’ karakteridir. Bu işaret yardımı ile derleyici dizginin nerede son bulduğunu anlar ve değişkene dizgi aktarımından sonra otomatik olarak koyulur. İşte bu sebeple tek bir A harfi hafıza da karakter olarak saklanırsa ASCII kod karşılığı olan 65 tamsayısı olarak saklanırken, A dizgisi iki karakter olarak –bir A harfi bir de NULL karakteri – saklanır. Bu nedenle 1’er den 2 byte yer kaplayacaktır.

Yine aynı sebepten dolayı (son karakter dizgi sonunu göstermek için işgal edildiğinden) karakter dizisi tanımlarken bize lazım olacak sayıdan 1 fazla tanımlamak gerekir. Çünkü en son yer NULL karakteri için kullanılacaktır.

Bir dizginin ekrana yazılması demek söylenen adresten başlanarak NULL (ya da \0) görünceye kadar ki karakterlerin arka arkaya yazılması demektir.

char *renk;

 renk = “Mavi”;

printf (“renk = %s”, &renk[2]);  /* renk = vi */

renk 0 1 2 3 4
m a v i \0

Bir Dizginin Karakter Sayısının Bulunması: Madem ki bir dizgi NULL ifadesi ile sonlanıyor, eğer dizginin ilk karakterinden başlayarak NULL görünceye kadar sayarsak dizginin kaç karakterden oluştuğunu bulabiliriz.

ÖRNEK: Klavyeden girilen bir kelimenin kaç karakterden oluştuğunu bulan bir fonksiyonu ana programla birlikte yazınız.

DİZGİ DİZİLERİ

Birden fazla dizgiyi tek bir isim altında saklamaya ihtiyaç duyabiliriz. Mesela 20 tane ismi saklamamız gerekebilir.

İSİM

“ALİ”
“VELİ”
“NESLİHAN”
“FATMA”

Aynı tipteki birden fazla değişkeni tek bir isim altında saklamak için dizileri kullandığımıza göre yine dizilerden faydalanmamız gerekecek. Ancak bir dizgi zaten bir karakter dizisi ifade ediyordu. Yani yukarıdaki her bir isim zaten kendi başına bir dizi.O zaman birden fazla dizgi için iki boyutlu bir karakter dizisi kullanmamız gerekecek. Aslında yukarıdaki 4 ismi saklayan yapı aslında 2 boyutlu bir dizi yapısıdır.

0 1 2 3 4 5 6 7 8
0 A L İ \0
1 V E L İ \0
2 N E S L İ H A N \0
3 F A T M A \0

Görüldüğü gibi aslında 4 tane ismi saklayan yapı 4 satır ve 9 sütundan oluşmuş çift boyutlu bir dizidir. Çift boyutlu diziler önce satır sonra da sütun boyutu verilerek tanımlandığına göre bu yapıyı aşağıdaki şekilde tanımlayabiliriz.

char isim[4] [9] = {“ALİ”, “VELİ”, “NESLİHAN”, “FATMA”};

Dizgi tanımlamak için göstericide kullanabildiğimize göre aynı tanımlamayı bir gösterici dizisi ile de yapabilirdik:

char * isim[4] = {“ALİ”, “VELİ”, “NESLİHAN”, “FATMA”};

Buradaki herbir isme ulaşmak için tek indis numarasını vermek yeterlidir.

printf (“1. İsim = %s ”, isim[0]); /* 0. satırda bulunan ismin tamamı yazılacak. 1. isim = ALİ */

Esasında isim [0] kullanımı yerine isim [0][0] ifadesi de kullanılabilir. Bununla ifade edilen, “söylenen adresten başlayıp NULL ifadesi görünceye kadar yaz” dır.

ÖRNEK: Klavyeden girilen 10 tane ismi giriş sırasının tersinden ekrana yazan programı kodlayınız.

 

 

Hakkında Yazılım Geliştiricileri


Beni Takip Et

Yorum ( 1 )

  1. 17.satırda scanf yerine printf olması gerekmiyor mu?

Leave a reply

CAPTCHA
Refresh

*