Memik Yanık - Kişisel Web Sitesi Ana Sayfa | Hakkımda | Kitap Önerileri | Fotoğraflarım | RSS RSS | İletişim

Delphi : 5. Ders; Class'lar Hakkında Önbilgi


Nesneye yönelik programcılık tekniklerine ve kavramlarına kayıtsız kalarak Delphi ile usta işi programlar yazmak mümkündür. Çünkü Delphi %100 veya saf nesneye yönelik bir programlama dili değildir ve kendiniz Component geliştirmediğiniz sürece fazla zorluk yaşamayabilirsiniz. 

C# ve C++ gibi programlama dillerinde en küçük program bile Class halinde düzenleniyor ve kodlar Class ile bloklanan alana yazılıyor. Delphi’de durum oldukça farklıdır. Şimdiye kadar verilen bilgilere göre Delphi’de uygulamalar DPR uzantılı proje dosyasından itibaren çalışmaya başlamaktadır. Proje dosyasında tanımlanan herhangi bir Class yoktur. Bütün kodları DPR uzantılı dosyaya yazmak mümkün olamayacağından Unit adı verilen PAS uzantılı modüller hazırlanıyor ve derleme anında bu modüller DPR uzantılı proje dosyasına bağlanarak EXE dosya oluşturuluyor. Class’lar ise Unit adı verilen kod dosyaları dahilinde hazırlanmaktadır.

Delphi’de nasıl Class hazırlanıp kullanıldığının kolay anlaşılmasını sağlamak için bu konuyu adım adım anlatacağım. Bu düşünce ile ilk olarak News Items diyalog kutusundaki Console Application şablonundan yararlanıp bir konsol uygulaması hazırladım. Console Application şablonu ile uygulama hazırlayıp kaydettiğinizde 4 dosya hazırlanmaktadır. Asıl program kodları DPR uzantılı dosyaya yazılmaktadır.

 

Bildiğiniz gibi Console Application şablonu ile hazırlanan uygulamaların DPR dosyasında $APPTYPE direktifi ile projenin konsol uygulaması olduğu işaret edilmektedir. Burada amacım konsol uygulaması hazırlamak olmadığı için bu direktifi sildim. Ayrıca bu projede gerek duymayacağım SysUtils adlı Unit’in uygulamaya dahil edilmesini engelleyebilirdim. Aşağıda verdiğim ekran görüntüsünde pencere başlığı olarak bdsproj uzantılı dosyanın(yeni sürümlerde dproj) seçilmekle birlikte içeriği görüntülenen dosya DPR uzantılı dosyadır.

 

Bu sırada bu uygulama çalıştırıldığında derleyici herhangi bir hata rapor etmez ama kullanıcı uygulamanın çalışıp durduğunu hissetmez bile. Yine bildiğiniz gibi Delphi uygulamasına bir form eklediğinizde Unit adı verilen PAS uzantılı bir kod dosyası hazırlanmaktadır. 

Formu temsil eden Unit’lerde Delphi’nin TForm sınıfını mirasçısı bir Class hazırlanmaktadır. Bu işlemi kendim yapmak istediğim için File menüsünden komut vererek yukarıda hazırladığım Delphi uygulamasına “Unit1” adında bir unit yani PAS uzantılı bir kod dosyası dahil ettim.



Gördüğünüz gibi Delphi’de Unit’lerde veya PAS uzantılı modüllerin “unit” anahtar kelimesi ile başlayan satırında Unit’e ad verilmektedir. Bu ad Delphi tarafından otomatik olarak verildiği için ilgilenmenize gerek yoktur. Kod dosyasını faklı bir ad ile kaydetmeniz halinde Unit’e verilen ad kendiliğinden değişir. Unit’lerin son satırında sonuna nokta(.) konulan End deyimi olmaktadır. 

Delphi’nin Unit adı verilen kod dosyalarında interface ve implementation bölgeleri bulunmaktadır. interface bölgesi implementation bölgesinin başladığı noktada sona ermektedir. Benzer şekilde implementation bölgesi, sonunda nokta olan End deyiminin kullanıldığı satırda bitmektedir. Kısaca belirtmek gerekirse; interface bölgesinde tanımlamalar, implementation bölgesinde ise asıl işlem yapan satırlar yani metotlar(procedure’ler veya fonksiyonlar) olmaktadır. Procedure veya fonksiyonlar Unit’in interface bölgesinde deklare edilip gövdeleri implementation bölgesine yazılır. 

Şimdi bu proje ve Unit’i adım adım File menüsünden komut verilerek yeni proje hazırlandığı zaman Delphi tarafından hazırlanan proje ve Unit’e benzeteceğim. Yapacağım eklemeler sayesinde proje çalıştırıldığı zaman ekrana bir formun gelmesini sağlayacağım. Bu sayede Delphi’nin Class’ları, Unit’leri ve formları hakkında temel bilgilere sahip olabileceksiniz. İlk olarak Unit’in interface bölgesinde Uses bloğuna yer verip gerek duyduğum hazır unit’leri koda dahil ettim.

 

Kendi hazırladığınız Unit’lerde Delphi’nin hangi hazır Unit’lerine gerek duyacaksanız onları dahil etmelisiniz. Bu şekilde gerek duyduğum Unit’lerin adlarını Uses bloğuna yazdıktan sonra interface bölgesinde Type bloğuna yer vereceğim. Bildiğiniz gibi Type bloğunda Record’lar ve Class’lar, başka bir deyişle tipler tanımlanabilmektedir. 

Buradaki amacım Delphi’nin TForm sınıfının mirasçısı bir Class hazırlamak olduğu için Class anahtar kelimesini aşağıdaki gibi kullanarak “Form_Class” adında bir Class hazırladım.

B
öyle bir anlatım şekline başka kaynaklarda rastlama imkanı olmasa bile yerli programcılık kitapları yazarlarından birisi mahkemeye başvurup "Unit1" adında Unit hazırlamıi olmakla unit adını çalmakla beni suçlarsa hiç sürpriz olmaz. Madem okurlarını zirvelere çıkarmakla ünlü yazara göre i, j, sayi1, sayi2, dizi, kayit adında değişken tanımlamak suçtur Unit’e Unit1 adını vermek hayla hayla suç olacaktır.

 

Burada yararlandığım veya mirasçı durumundaki Delphi’nin “TForm” adlı Class’ı Forms adlı Unit’te bulunmaktadır. Bu unit Uses bloğuna yazılmazsa TForm sınıfından bu şekilde yararlanılamaz. Bu şekilde Unit’te class hazırladıktan sonra DPR uzantılı proje dosyasına geçtim. DPR uzantılı proje dosyasında ilk olarak Uses bloğuna yer verip Unit1’i DPR dosyası içinde kullanmak istediğimi işaret ettim. Proje dosyasında ayrıca Forms adlı hazır Unit’e gerek vardır.

 

Şimdi sırada Unit1.pas’ta tanımlı olan ve “Form_Class” adını verdiğim Class’ın örneğini almak veya bu Class’tan yola çıkarak nesne hazırlamak var. Bu hazırlığı Delphi’nin geleneksel yöntemi ile yapacağım. Bildiğiniz gibi konsol uygulaması olmayan Delphi projeleri çalıştırıldığı zaman derleyici otomatik olarak Application nesnesi hazırlamaktadır. Bu nedenle otomatik olarak hazırlanan Application nesnesini Initialize metodu ile başlattım.

 

DPR dosyası bu şekilde düzenlenen proje çalıştırıldığında herhangi bir hata rapor edilmez ve uygulamanın çalışması ile durması bir olur. TApplication sınıfının Initialize metodu ile başlatılan uygulamanın çalışmasının hemen sona ermesini engellemek için forma ihtiyaç vardır. Unit1’deki “Form_Class” adlı sınıfın örneğini alırken veya bu sınıftan yola çıkıp nesne hazırlarken TApplication sınıfının CreateForm() metodunu kullanacağım. 

2 parametreye sahip olan CreateForm() metodu ilk parametre olarak hazırlanacak forma kaynaklık edecek Class’ın adını almaktır. 2. parametrede ise söz konusu Class tipindeki değişken işaret edilmektedir. Bu nedenle DPR uzantılı proje dosyasında Var bloğuna yer verip “Form_Class” tipinde bir değişken tanımladım ve bu değişkeni CreateForm() metoduna 2. parametre olarak verdim. Bu işlemi nasıl yaptığımı aşağıda görebilirsiniz.

 

Aslında TApplication sınıfının CreateForm() metodu birden fazla işlemi bir seferde yapmaktadır. Kendisine 1. parametre olarak verilen sınıfın örneğini alıp Application nesnesine eklemektedir. Bu hali ile bu proje çalıştırıldığında hata meydana gelir. Çünkü CreateForm() metodu TForm’dan türetilmiş sınıfın örneğini alırken DFM dosyasına gerek duyar. 

Hatırlayacağınız gibi DFM dosyalarında formların ve formların üzerine yerleştirilen nesnelerin görsel yapısı ile ilgili bilgiler bulunmaktadır. Burada örneğini almak istediğim “Form_Class” sınıfı “Unit1.Pas” dosyasında tanımlı olduğu için Not Defteri ile aşağıdaki gibi Text dosyası hazırlayıp “Unit1.dfm” adıyla proje dosyasını sakladığım klasöre kaydettim.

 

Bu şekilde DFM dosyası hazırladıktan sonra proje dosyasında $R direktifi ile bu dosyanın derleme sırasında projeye dahil edilmesini sağladım. Anlatılan şekilde CreateForm() metodu ile “Form1” adında ve TForm tipinde bir nesne hazırlayıp Application nesnesiyle ilişkilendirdikten sonra Run metodu ile Application nesnesini veya uygulamayı çalıştırdım.

uses
  Forms,
  Unit1 in 'Unit1.pas';
Var
  Form1 : Form_Class;
{$R Unit1.DFM}
begin
   Application.Initialize;
   Application.CreateForm(Form_Class, Form1);
   Application.Run;
end.

Sanırım Delphi uygulamalarında geri planda nelerin geliştiği böylece biraz anlaşıldı. Bu şekilde düzenlenen proje çalıştırıldığında ekrana aşağıdaki gibi bir form gelir.



Şimdi ise kendi hazırladığım ve “Form_Class” adını verdiğim sınıfın örneğini başka bir teknikle hazırlayıp ekrana getireceğim. Başka bir deyişle TApplication sınıfının CreateForm() metodunu kullanmayacağım. DPR uzantılı proje dosyası aşağıda gibi düzenlenirse “Form_Class” adını verdiğim sınıfın örneği(yani nesne hazırlanır) hazırlanır ve hazırlanan form nesnesi ShowModal metodu ile ekrana getirilir.

program Project1;
uses
  Forms,Unit1 in 'Unit1.pas';
Var
  Form1 : Form_Class;
  {$R Unit1.DFM}
begin
  Form1 := Form_Class.Create(Application);
  Application.Initialize;
  Application.Run;
  Form1.ShowModal;
end. 

N
esne oluşturmak ve yok etmek için burada kullandığımız Create ve Free metotları temel sınıf olan TObject sınıfı kaynaklıdır. Yani yeni bir sınıf tanımlarken ister istemez TObject sınıfından türetme yapıyoruz ve TObject sınıfına ait metotları kullanıyoruz. Create ve Free metotları bizim için hafızada yer ayırma ve serbest bırakma işlemlerini yaparlar.

Bu şekilde Delphi uygulamalarında geri planında gelişen olaylar hakkında biraz bilgi sahibi olduktan sonra Delphi’de nesneye yönelik programcılığın temeli olan Class’lar hakkında bilgi vermeye kaldığım yerden devam edeceğim. Bu amaçla File menüsünden New-VCL Forms Application komutunu vererek yeni bir proje hazırladım.

Bildiğiniz gibi yeni bir proje hazırlandığında projeye “Unit1” adında bir Unit dahil edilmekte ve “pas” uzantılı bu kod dosyasına aşağıda verilen satırlar otomatik olarak dahil edilmektedir. Bu satırları dikkatlice incelerseniz Type bloğunda Class() deyimi sayesinde Delphi’nin TForm sınıfından yola çıkılarak “TForm1” adında bir sınıf hazırlanmaktadır.

 

Type bloğunda sınıf deklare edildikten sonra sınıfın Private ve Puclic üyelerinin yazılacağı yerler işaret edilmektedir. Bu sınıfla ilgili tanımlamalar blok sonunu işaret eden End; deyiminin kullanıldığı satırda sona ermektedir. Yukarıda kendi hazırladığım Class’ta Private ve Public üyelerin tanımlanacağı yerleri işaret etmeye gerek duymadım.

Projeye dahil edilen form için yukarıda işaret edildiği gibi sınıf hazırlandıktan sonra Unit’in Var bloğunda bu sınıftan yararlanılarak “Form1” adında bir nesne hazırlanmaktadır. Nesne hazırlandıktan sonra nesne ile ilgili istenen işlemler yapılabilir. “TForm1” class’ından yola çıkılarak “Form1” adında nesnenin hazırlandığı satırı aşağıda görebilirsiniz. Sınıftan yola çıkılarak nesne hazırlamak veya sınıfın örneğini almak değişken tanımlamak gibidir.

 


İlk bakışta yukarıda verilen(italik paragraf) paragraf doğru gibi görünmektedir. Ancak nesneye yönelik program geliştirme tecrübesi olanlar bu paragraftaki eksikliği fark etmiş olmalıdır. Borland nesneye yönelik program geliştirme tekniklerine veya kavramlarına uzak durmak isteyen programcılara destek olmak için bazı işlemleri gözden uzakta yapmaktadır. Normalde bir sınıftan yola çıkarak değişken tanımlanıp bellekte rezervasyon yapıldıktan sonra 2. bir işlem ile nesnenin hazırlanması gerekir. Delphi’de form nesnesi hazırlama işlemi DPR uzantılı proje dosyasında yapılmaktadır.

 

Unit’in Var bloğunda değişken tanımlandıktan sonra proje dosyasında TApplication sınıfının CreateForm() metodu ile Class’tan yola çıkılıp nesne hazırlanmaktadır. Unit’in Var bloğunda tanımlanan değişkenler global olduğu, başka bir deyişle proje dosyasında ve diğer Unit’lerde yaşadıkları için hata meydana gelmez. 

TAppication sınıfının CreateForm() metodu 2 parametreye sahiptir. İlk parametrede form nesnesi hazırlanırken yararlanılacak sınıf belirtilmekte ve 2. parametrede ise söz konusu sınıftan yararlanarak tanımlanan değişken işaret edilmektedir. Bu konu üzerinde düşünmenizi sağlamak amacıyla Unit1’deki Var bloğunu DPR uzantılı proje dosyasına taşıyacağım.




Sizce değişen bir şey oldu mu? Projenin orijinal halinde Unit1’de “TForm1” adı verilen class hazırlanıp bu Class’tan yola çıkarak nesne hazırlanırken gerek duyulacak değişken tanımlanırken, proje dosyasında ise CreateForm() metodu ile nesne hazırlama işlemi yapılıyordu. 

Bu hali ile proje dosyasında hem nesne için değişken tanımlanmakta hem de nesne hazırlanmaktadır. Bu şekilde düzenlenen proje dosyası herhangi bir hataya neden olmaz ve proje çalıştırıldığında ekrana yine “Form1” gelir.

Şimdi şeytanın avukatlığını yapıp projenin ilk formu ekrana gelmeden önce bir diyalog kutusu ile kullanıcıya mesaj vereceğim. ShowMessage() deyimi veya metodu Dialogs adlı Unit’te tanımlı olduğu için proje dosyasına dahil ettim.

 

DPR uzantılı proje dosyasında yaptığım bu değişiklikten sonra proje çalıştırılırsa ekrana önce ShowMessage() deyimi ile mesaj getirilir. ShowMessage deyimi ile ekrana getirilen diyalog kutusu kapatıldıktan sonra Application nesnesinin CreateForm() metodu ile “Form1” nesnesi hazırlanıp ekrana getirilir.

Yeni bir proje hazırlandığında TApplication tipinde Application nesnesi otomatik olarak hazırlanıyor. TApplication sınıfının Initialize metodu ile Application nesnesi hazırlanıp Run metodu ile çalıştırılıyor. TApplication sınıfı “Forms” adlı Unit’te tanımlıdır. Application nesnesi hakkında bilgi sahibi olmanız için Delphi tarafından hazırlanan Application nesnesi yerine kendim bir Application nesnesi hazırlayıp kullanacağım. Bu amaçla DPR dosyasının Var bloğunda TApplication tipinde bir değişken tanımladım. 

program Project1;
uses
  Forms, Dialogs,
  Unit1 in 'Unit1.pas' {Form1};
{$R *.res}
var
  Form1: TForm1;
  Uygulama : TApplication;
begin
  Uygulama := TApplication.Create(Application);
  ShowMessage('Uygulamayı Çalıştırdınız');
  Uygulama.CreateForm(TForm1, Form1);
  Uygulama.Run;
end.

Biraz Reklam

Delphi hakkında ayrıntılı bilgi edinmek istiyorsanız aşağıda resmini verdiğim Delphi 2007 kitabıma bakabilirsiniz. En kapsamlı Delphi kitabı iddiası ile hazırlanan bu kitabı kitapçılardan, Seçkin Yayıncılıktan veya HepsiBurada.com'dan temin edebilirsiniz.

 

Programcılık Dersleri 27.07.2009 19:04:23

YORUM YOK


YorumlarYorum Yaz
Ana Sayfa | Hakkımda | Kitap Önerileri | Fotoğraflarım | RSS | İletişim
Memik Yanık 2004-2009 © Tüm Hakları Saklıdır.
Hazırlayan www.semgoksu.com