Nesneye dayalı program yapıyoruz ama gerçekte programlarımız ne kadar nesneye dayanıyor ki?
Nyp'nin temel bir çok özelliğini bilmemize rağmen bunu programlarımızda yeteri kadar kullanmıyoruz. Kendi nesnelerimiz yerine Delphi'nin bize sunmuş olduğu hazır bileşenlerle işimizi görmeye çalışıyoruz. Onlarda bi yere kadar ...
Şimdi nesnelerle ilgili ufak bir örnek yapıp ardından bunun avantajlarına ve dezavantajlarına değinecez.
Hikayemiz de bir bankada yapılan havale işleminin gerçekleştirilmesi olsun.
Bu işlemde bir hesaptan başka bir hesaba belirtilen miktarda parayı transfer etmemiz gerekiyor. Bize lazım olan bilgiler :
1- Havale yapan hesap no
2- Havale yapılacak hesap no
3- Havale yapılacak miktar
Şimdi THavale sınıfımızın tanımını yazalım.
Kod: Tümünü seç
type
THavale = class
private
fHavaleYapanCariID :Integer;
fHavaleYapilanCariID :Integer;
fHavaleYapilanMiktar :Double;
function GetHavaleYapanCariID: Integer;
procedure SetHavaleYapanCariID(const Value: Integer);
function GetHavaleYapilanCariID: Integer;
procedure SetHavaleYapilanCariID(const Value: Integer);
function GetHavaleYapilanMiktar: Double;
procedure SetHavaleYapilanMiktar(const Value: Double);
public
Procedure HavaleYap;
property HavaleYapanCariID : Integer read GetHavaleYapanCariID write SetHavaleYapanCariID;
property HavaleYapilanCariID : Integer read GetHavaleYapilanCariID write SetHavaleYapilanCariID;
property HavaleYapilanMiktar : Double read GetHavaleYapilanMiktar write SetHavaleYapilanMiktar;
end;
Şimdi de metod ve fonksiyonların gövdelerini yazalım.
Kod: Tümünü seç
{ THavale }
function THavale.GetHavaleYapanCariID: Integer;
begin
Result := fHavaleYapanCariID;
end;
function THavale.GetHavaleYapilanCariID: Integer;
begin
Result :=fHavaleYapilanCariID;
end;
function THavale.GetHavaleYapilanMiktar: Double;
begin
Result := fHavaleYapilanMiktar;
end;
procedure THavale.SetHavaleYapanCariID(const Value: Integer);
begin
fHavaleYapanCariID := Value;
end;
procedure THavale.SetHavaleYapilanCariID(const Value: Integer);
begin
fHavaleYapilanCariID := Value;
end;
procedure THavale.SetHavaleYapilanMiktar(const Value: Double);
begin
fHavaleYapilanMiktar := Value;
end;
HavaleYap metodunu yazarken eksik olan bir şey farkttim. HavaleYap metodu sonuçta kendisine gelen verileri kullanarak bi Sql ifadesi oluşturup bunu veritabanına gönderecekti ama nesnenin veritabanı ile iletişim kurması için her hangi bir özelliği yoktu. Bu nedenle nesnemizin özelliklerine Veritabanı adında bir alan eklemeye karar verdim. Veritabanı olarakta Firebird / IBX kullandığımdan bu alanın tipini TIBDatabase olarak ayarladım.
Kod: Tümünü seç
type
THavale = class
private
fHavaleYapanCariID :Integer;
fHavaleYapilanCariID :Integer;
fHavaleYapilanMiktar :Double;
fIBDatabase :TIBDatabase; //
...
...
...
function GetVeritabani: TIBDatabase;
procedure SetVeritabani(const Value: TIBDatabase);
public
...
...
...
property Veritabani : TIBDatabase read GetVeritabani write SetVeritabani;
end;
...
...
function THavale.GetVeritabani: TIBDatabase;
begin
Result :=fIBDatabase;
end;
procedure THavale.SetVeritabani(const Value: TIBDatabase);
begin
fIBDatabase := Value;
end;
Kod: Tümünü seç
type
THavale = class
private
fHavaleYapanCariID :Integer;
fHavaleYapilanCariID :Integer;
fHavaleYapilanMiktar :Double;
fIBDatabase :TIBDatabase;
fIbSql : TIBSQL; //
...
...
Kod: Tümünü seç
procedure THavale.HavaleYap;
begin
IBSqlOlustur;
if fibsql.Transaction.InTransaction = False Then
fibsql.Transaction.StartTransaction;
try
try
fibsql.Close;
fibsql.SQL.Clear;
fibsql.SQL.Add('Update CARI set BAKIYE = BAKIYE + :P_BAKIYE' );
fibsql.SQL.Add('Where ID = :P_CARIID');
fibsql.Params[0].AsFloat := HavaleYapilanMiktar;
fibsql.Params[1].AsInteger := HavaleYapilanCariID;
fibsql.ExecQuery;
fibsql.Close;
fibsql.SQL.Clear;
fibsql.SQL.Add('Update CARI set BAKIYE = BAKIYE - :P_BAKIYE');
fibsql.SQL.Add('Where ID = :P_CARIID');
fibsql.Params[0].AsFloat := HavaleYapilanMiktar;
fibsql.Params[1].AsInteger := HavaleYapanCariID;
fibsql.ExecQuery;
fibsql.Transaction.CommitRetaining;
except
fibsql.Transaction.RollbackRetaining;
Raise Exception.Create('Dikkat!!! Havale işlemi başarılı olamadı...');
end;
finally
IBSqlYokEt;
end;
end;
procedure THavale.IBSqlOlustur;
begin
if not Assigned(fIBDatabase) Then
Raise Exception.Create('Bağlanılacak Veritabanı bulunamadı. İşlem iptal ediliyor !!!');
if Assigned(fibsql) Then Exit;
fIbSql := TIBSQL.Create(nil);
fIbSql.Database := Veritabani;
fIbSql.Transaction := Veritabani.DefaultTransaction;
end;
procedure THavale.IBSqlYokEt;
begin
FreeAndNil(fibsql);
end;
Form1.dfm
Kod: Tümünü seç
object Form1: TForm1
Left = 256
Top = 248
Width = 382
Height = 212
Caption = 'Havale'
Color = clBtnFace
Font.Charset = DEFAULT_CHARSET
Font.Color = clWindowText
Font.Height = -11
Font.Name = 'MS Sans Serif'
Font.Style = []
OldCreateOrder = False
OnCreate = FormCreate
PixelsPerInch = 96
TextHeight = 13
object Label1: TLabel
Left = 32
Top = 22
Width = 93
Height = 13
Caption = 'Havale Yapan Kişi :'
end
object Label2: TLabel
Left = 28
Top = 52
Width = 97
Height = 13
Caption = 'Havale Yapılan Kişi :'
end
object Label3: TLabel
Left = 3
Top = 84
Width = 122
Height = 13
Caption = 'Havale Yapılacak Miktar :'
end
object btnHavaleYap: TButton
Left = 214
Top = 112
Width = 147
Height = 25
Caption = 'Havale Yap'
TabOrder = 0
OnClick = btnHavaleYapClick
end
object DBLookupComboBox1: TDBLookupComboBox
Left = 136
Top = 18
Width = 225
Height = 21
KeyField = 'ID'
ListField = 'AD;SOYAD'
ListSource = DataSource1
TabOrder = 1
end
object DBLookupComboBox2: TDBLookupComboBox
Left = 136
Top = 48
Width = 225
Height = 21
KeyField = 'ID'
ListField = 'AD;SOYAD'
ListSource = DataSource1
TabOrder = 2
end
object Edit1: TEdit
Left = 136
Top = 80
Width = 225
Height = 21
TabOrder = 3
end
object IBDatabase1: TIBDatabase
Connected = True
DatabaseName = 'F:\Developers\Delphi\Samples\OOP\Ornek1\DATA2.GDB'
Params.Strings = (
'user_name=sysdba'
'password=masterkey'
'lc_ctype=WIN1254')
LoginPrompt = False
DefaultTransaction = IBTransaction1
Left = 8
Top = 144
end
object IBTransaction1: TIBTransaction
Active = True
DefaultDatabase = IBDatabase1
Params.Strings = (
'read_committed'
'rec_version'
'nowait')
Left = 40
Top = 144
end
object IBDataSet1: TIBDataSet
Database = IBDatabase1
Transaction = IBTransaction1
SelectSQL.Strings = (
'select * from CARI')
Active = True
Left = 72
Top = 144
object IBDataSet1ID: TIntegerField
FieldName = 'ID'
Origin = '"CARI"."ID"'
ProviderFlags = [pfInUpdate, pfInWhere, pfInKey]
Required = True
end
object IBDataSet1AD: TIBStringField
FieldName = 'AD'
Origin = '"CARI"."AD"'
end
object IBDataSet1SOYAD: TIBStringField
FieldName = 'SOYAD'
Origin = '"CARI"."SOYAD"'
end
object IBDataSet1BAKIYE: TIBBCDField
FieldName = 'BAKIYE'
Origin = '"CARI"."BAKIYE"'
Precision = 18
Size = 2
end
end
object DataSource1: TDataSource
DataSet = IBDataSet1
Left = 104
Top = 144
end
end
Bu da kullandığımız tablo...
Kod: Tümünü seç
CREATE TABLE CARI (
ID INTEGER NOT NULL,
AD VARCHAR(20) COLLATE PXW_TURK,
SOYAD VARCHAR(20) COLLATE PXW_TURK,
BAKIYE NUMERIC(15,2)
);
Form üstünde 2 adet DBLookupComboBox var. Bunların yardımıyla sırasyıla havale yapan ve yapılan kişileri listeden seçebileceğiz. Hemen alttaki edit bileşenine de yapmak istediğimiz havale miktarını girip düğmemize tıkladığımızda devreye nesnemiz girecek ve havale işlemini gerçekleştirecektir.
Kod: Tümünü seç
procedure TForm1.btnHavaleYapClick(Sender: TObject);
var
Havale :THavale;
begin
Havale :=THavale.Create;
try
Havale.Veritabani :=IBDatabase1;
Havale.HavaleYapanCariID :=DBLookupComboBox1.KeyValue;
Havale.HavaleYapilanCariID :=DBLookupComboBox2.KeyValue;
Havale.HavaleYapilanMiktar :=StrToFloat(edit1.Text);
Havale.HavaleYap;
ShowMessage('Havale Başarılı');
finally
FreeAndNil(Havale);
end;
end;
Kendi oluşturduğumuz nesneyi kullanmadan bu işi nasıl yapardık ?
Kod: Tümünü seç
procedure TForm1.btnHavaleYapClick(Sender: TObject);
begin
if IBSQL1.Transaction.InTransaction = False Then
IBSQL1.Transaction.StartTransaction;
try
IBSQL1.Close;
IBSQL1.SQL.Clear;
IBSQL1.SQL.Add('Update CARI set BAKIYE = BAKIYE + :P_BAKIYE' );
IBSQL1.SQL.Add('Where ID = :P_CARIID');
IBSQL1.Params[0].AsFloat := strtofloat(Edit1.Text);
IBSQL1.Params[1].AsInteger := DBLookupComboBox1.KeyValue;
IBSQL1.ExecQuery;
IBSQL1.Close;
IBSQL1.SQL.Clear;
IBSQL1.SQL.Add('Update CARI set BAKIYE = BAKIYE - :P_BAKIYE');
IBSQL1.SQL.Add('Where ID = :P_CARIID');
IBSQL1.Params[0].AsFloat := strtofloat(Edit1.Text);
IBSQL1.Params[1].AsInteger := DBLookupComboBox2.KeyValue;
IBSQL1.ExecQuery;
IBSQL1.Transaction.CommitRetaining;
except
IBSQL1.Transaction.RollbackRetaining;
Raise Exception.Create('Dikkat!!! Havale işlemi başarılı olamadı...');
end;
end;
İki -procedure TForm1.btnHavaleYapClick(Sender: TObject); - metodu bi karşılaştıralım.













Bu kadar sebep yetmez mi ?

-------------------------------------------
Günün birinde size dedilerki "Bakiyesi yeterli olmayan insanlar havale yapamazlar !". Ne yapacaksınız ?
Çok basit...
Nesnenin olduğu uniti açalım ve nesnenin private alanına
Kod: Tümünü seç
...
fIbQuery : TIBQuery;
...
Function HavaleYapacakKisininYeterliBakiyesiVarmi:Boolean;
...
Kod: Tümünü seç
function THavale.HavaleYapacakKisininYeterliBakiyesiVarmi: Boolean;
begin
fIbQuery := TIBQuery.Create(nil);
try
Result := False;
fIbQuery.Database := fIBDatabase;
fIbQuery.Transaction := fIBDatabase.DefaultTransaction;
fIbQuery.Close;
fIbQuery.SQL.Clear;
fIbQuery.SQL.Add('Select BAKIYE FROM CARI WHERE ID =' + IntToStr(HavaleYapanCariID));
fIbQuery.Open;
Result := fIbQuery.Fields[0].AsFloat - HavaleYapilanMiktar >= 0.00;
finally
FreeAndNil(fIbQuery);
end;
end;
Kod: Tümünü seç
procedure THavale.HavaleYap;
begin
IBSqlOlustur;
if HavaleYapacakKisininYeterliBakiyesiVarmi = False Then
Raise Exception.Create('İşlem yapacak kişinin bakiyesi yeterli değil. İşlem iptal ediliyor !!!');
if fibsql.Transaction.InTransaction = False Then
fibsql.Transaction.StartTransaction;
...
...
------------------------------------
Yine bir gün size "Bundan sonra havale işlemlerinde havale yapan kişiden yaptığı havale miktarının % 1 'i işlem ücreti olarak kesilecek" dediler. Desinler mesele yok

Kod: Tümünü seç
THavale = class
private
fHavaleYapanCariID :Integer;
fHavaleYapilanCariID :Integer;
fHavaleUcreti : Double; //--> havale ücreti
fHavaleYapilanMiktar :Double;
fIBDatabase :TIBDatabase;
fIbSql : TIBSQL;
fIbQuery : TIBQuery;
...
...
procedure THavale.HavaleYap;
begin
IBSqlOlustur;
...
...
fibsql.ExecQuery;
fHavaleUcreti := HavaleYapilanMiktar / 100; //--> ***
fibsql.Close;
fibsql.SQL.Clear;
fibsql.SQL.Add('Update CARI set BAKIYE = BAKIYE - :P_BAKIYE');
fibsql.SQL.Add('Where ID = :P_CARIID');
fibsql.Params[0].AsFloat := HavaleYapilanMiktar - fHavaleUcreti; //-->***
fibsql.Params[1].AsInteger := HavaleYapanCariID;
fibsql.ExecQuery;
...
...

Not: Bu nesnenin Dunit kullanarak nasıl test edilebileceğini de en yakın zamanda buraya yazmaya çalışırım.
UnitHavale.pas
Kod: Tümünü seç
unit UnitHavale;
interface
uses
SysUtils,IBDatabase,ibsql,IBQuery;
type
THavale = class
private
fHavaleYapanCariID :Integer;
fHavaleYapilanCariID :Integer;
fHavaleUcreti : Double;
fHavaleYapilanMiktar :Double;
fIBDatabase :TIBDatabase;
fIbSql : TIBSQL;
fIbQuery : TIBQuery;
function GetHavaleYapanCariID: Integer;
procedure SetHavaleYapanCariID(const Value: Integer);
function GetHavaleYapilanCariID: Integer;
procedure SetHavaleYapilanCariID(const Value: Integer);
function GetHavaleYapilanMiktar: Double;
procedure SetHavaleYapilanMiktar(const Value: Double);
Function HavaleYapacakKisininYeterliBakiyesiVarmi:Boolean;
function GetVeritabani: TIBDatabase;
procedure SetVeritabani(const Value: TIBDatabase);
Procedure IBSqlOlustur;
Procedure IBSqlYokEt;
public
Procedure HavaleYap;
property HavaleYapanCariID : Integer read GetHavaleYapanCariID write SetHavaleYapanCariID;
property HavaleYapilanCariID : Integer read GetHavaleYapilanCariID write SetHavaleYapilanCariID;
property HavaleYapilanMiktar : Double read GetHavaleYapilanMiktar write SetHavaleYapilanMiktar;
property Veritabani : TIBDatabase read GetVeritabani write SetVeritabani;
end;
implementation
{ THavale }
function THavale.GetHavaleYapanCariID: Integer;
begin
Result := fHavaleYapanCariID;
end;
function THavale.GetHavaleYapilanCariID: Integer;
begin
Result :=fHavaleYapilanCariID;
end;
function THavale.GetHavaleYapilanMiktar: Double;
begin
Result := fHavaleYapilanMiktar;
end;
function THavale.GetVeritabani: TIBDatabase;
begin
Result :=fIBDatabase;
end;
procedure THavale.HavaleYap;
begin
IBSqlOlustur;
if HavaleYapacakKisininYeterliBakiyesiVarmi = False Then
Raise Exception.Create('İşlem yapacak kişinin bakiyesi yeterli değil. İşlem iptal ediliyor !!!');
if fibsql.Transaction.InTransaction = False Then
fibsql.Transaction.StartTransaction;
try
try
fibsql.Close;
fibsql.SQL.Clear;
fibsql.SQL.Add('Update CARI set BAKIYE = BAKIYE + :P_BAKIYE' );
fibsql.SQL.Add('Where ID = :P_CARIID');
fibsql.Params[0].AsFloat := HavaleYapilanMiktar;
fibsql.Params[1].AsInteger := HavaleYapilanCariID;
fibsql.ExecQuery;
fHavaleUcreti := HavaleYapilanMiktar / 100;
fibsql.Close;
fibsql.SQL.Clear;
fibsql.SQL.Add('Update CARI set BAKIYE = BAKIYE - :P_BAKIYE');
fibsql.SQL.Add('Where ID = :P_CARIID');
fibsql.Params[0].AsFloat := HavaleYapilanMiktar - fHavaleUcreti;
fibsql.Params[1].AsInteger := HavaleYapanCariID;
fibsql.ExecQuery;
fibsql.Transaction.CommitRetaining;
except
fibsql.Transaction.RollbackRetaining;
Raise Exception.Create('Dikkat!!! Havale işlemi başarılı olamadı...');
end;
finally
IBSqlYokEt;
end;
end;
function THavale.HavaleYapacakKisininYeterliBakiyesiVarmi: Boolean;
begin
fIbQuery := TIBQuery.Create(nil);
try
Result := False;
fIbQuery.Database := fIBDatabase;
fIbQuery.Transaction := fIBDatabase.DefaultTransaction;
fIbQuery.Close;
fIbQuery.SQL.Clear;
fIbQuery.SQL.Add('Select BAKIYE FROM CARI WHERE ID =' + IntToStr(HavaleYapanCariID));
fIbQuery.Open;
Result := fIbQuery.Fields[0].AsFloat - HavaleYapilanMiktar >= 0.00;
finally
FreeAndNil(fIbQuery);
end;
end;
procedure THavale.IBSqlOlustur;
begin
if not Assigned(fIBDatabase) Then
Raise Exception.Create('Bağlanılacak Veritabanı bulunamadı. İşlem iptal ediliyor !!!');
if Assigned(fibsql) Then Exit;
fIbSql := TIBSQL.Create(nil);
fIbSql.Database := Veritabani;
fIbSql.Transaction := Veritabani.DefaultTransaction;
end;
procedure THavale.IBSqlYokEt;
begin
FreeAndNil(fibsql);
end;
procedure THavale.SetHavaleYapanCariID(const Value: Integer);
begin
fHavaleYapanCariID := Value;
end;
procedure THavale.SetHavaleYapilanCariID(const Value: Integer);
begin
fHavaleYapilanCariID := Value;
end;
procedure THavale.SetHavaleYapilanMiktar(const Value: Double);
begin
fHavaleYapilanMiktar := Value;
end;
procedure THavale.SetVeritabani(const Value: TIBDatabase);
begin
fIBDatabase := Value;
end;
end.
Unit1.pas
Kod: Tümünü seç
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls, DBCtrls, DB, IBCustomDataSet, IBDatabase, IBSQL,
IBQuery;
type
TForm1 = class(TForm)
btnHavaleYap: TButton;
Label1: TLabel;
Label2: TLabel;
DBLookupComboBox1: TDBLookupComboBox;
DBLookupComboBox2: TDBLookupComboBox;
Label3: TLabel;
Edit1: TEdit;
IBDatabase1: TIBDatabase;
IBTransaction1: TIBTransaction;
IBDataSet1: TIBDataSet;
IBDataSet1ID: TIntegerField;
IBDataSet1AD: TIBStringField;
IBDataSet1SOYAD: TIBStringField;
IBDataSet1BAKIYE: TIBBCDField;
DataSource1: TDataSource;
procedure FormCreate(Sender: TObject);
procedure btnHavaleYapClick(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
var
Form1: TForm1;
implementation
uses UnitHavale;
{$R *.dfm}
procedure TForm1.FormCreate(Sender: TObject);
begin
IBDataSet1.FetchAll;
end;
procedure TForm1.btnHavaleYapClick(Sender: TObject);
var
Havale :THavale;
begin
Havale :=THavale.Create;
try
Havale.Veritabani :=IBDatabase1;
Havale.HavaleYapanCariID :=DBLookupComboBox1.KeyValue;
Havale.HavaleYapilanCariID :=DBLookupComboBox2.KeyValue;
Havale.HavaleYapilanMiktar :=StrToFloat(edit1.Text);
Havale.HavaleYap;
ShowMessage('Havale Başarılı');
finally
FreeAndNil(Havale);
end;
end;
end.