Pola Pengamat di Delphi memperluas pola dasar Pengamat. Untuk informasi lebih lanjut tentang mode Pengamat, silakan merujuk ke [Gam+, halaman 293..303]
Mendefinisikan hubungan ketergantungan satu-ke-banyak antar objek. Ketika keadaan suatu objek berubah, semua objek yang bergantung padanya akan diberitahu dan diperbarui secara otomatis.
Memisahkan suatu sistem menjadi serangkaian kelas yang bekerja sama memiliki efek samping tertentu: konsistensi antara objek terkait harus dilindungi. Kami tidak ingin memasangkan tipe secara ketat demi konsistensi dimensi, karena hal ini akan mengurangi kegunaannya kembali. [Permainan+, hal293].
Peristiwa Delphi (alamat metode sebenarnya) memungkinkan Anda memiliki struktur yang baik untuk menangani masalah ini. Peristiwa memungkinkan Anda menghilangkan penggandengan dan mencapai penggandengan yang lebih baik. Misalnya: peristiwa TButton.OnClick dikirim untuk menyelesaikan pekerjaan terkait. Tapi kelas tidak menyimpan referensi ke event handler. Dalam pola pengamat, kelas yang mengirimkan peristiwa disebut objek sasaran (subjek), dan kelas yang mengendalikan peristiwa disebut pengamat (observer)
Peristiwa di Delphi dapat menghilangkan penggabungan kelas dengan lebih baik. Jika Anda ingin mengontrol beberapa peristiwa dan merujuk ke mode pengamat, Anda dapat membuat mekanisme pemberitahuan satu-ke-banyak. Sebuah target dapat memiliki sejumlah pengamat. Semua pengamat menerima pemberitahuan ketika keadaan target berubah. Setelah pengamat menerima notifikasi, ia segera menanyakan objek target untuk menjaga sinkronisasi dengan objek target.
Interaksi ini disebut juga terbitkan-berlangganan, dan targetnya adalah penerbit notifikasi. Ia tidak perlu mengetahui siapa pengamatnya ketika menemukan notifikasi. Sejumlah pengamat dapat berlangganan dan menerima notifikasi.
Aplikasi mode pengamat ini akan memberi Anda keuntungan mekanisme event Delphi dalam menangani penggandengan kelas. Struktur satu-ke-banyak mendaftarkan pengamat melalui pendaftaran dan pembatalan pendaftaran. Mekanisme satu-ke-banyak sebenarnya diterapkan berdasarkan iterator.
Misalkan Anda memiliki kelas Tsubject yang mendefinisikan perilaku yang bermakna. Pertama mari kita lihat kode demo mode pengamat:
jenis
TSubjek = kelas (TObject)
Pribadi
Server FO: TList;
publik
prosedur RegisterObserver(Pengamat: TSubjectObserver);
prosedur UnregisterObserver(Pengamat: TSubjectObserver);
akhir;
TSubjectObserver = kelas (TComponent)
pribadi
Diaktifkan: Boolean;
diterbitkan
properti Diaktifkan: Boolean baca FEnabled tulis FEnabled default Benar;
akhir;
Di antara antarmuka di atas:
? Mekanisme pendaftaran untuk mendaftarkan pengamat untuk Tsubject.
¨ FObservers: TList; menyimpan pengamat terdaftar.
¨ RegisterObserver(..) digunakan untuk mendaftarkan pengamat dan menambahkannya ke Fobserver.
¨ UnregisterObserver(..) digunakan untuk membatalkan pendaftaran pengamat dan menghapus objek terkait dari Fobserver.
?Mode pengamat juga perlu membuat kelas baru TsubjectObserver
¨ Kelas ini merupakan turunan dari Tcomponent.
¨ .Properti Enabled mengaktifkan atau menonaktifkan observasi. .
Penerapan sebenarnya dari mode pengamat berikut:
prosedur TSubject.RegisterObserver(Pengamat: TSubjectObserver);
mulai
jika FObservers.IndexOf(Observer) = -1 maka
FObservers.Add(Pengamat);
akhir;
prosedur TSubject.UnregisterObserver(Pengamat: TSubjectObserver);
mulai
FObservers.Hapus(Pengamat);
akhir;
Implementasi shangguan mendukung bagian registrasi pengamat. Di manakah mekanisme notifikasi one-to-many? Untuk aplikasi notifikasi satu-ke-banyak yang sebenarnya, Anda dapat menentukan metode Perubahan untuk Tsubject untuk memberi tahu pengamat terdaftarnya, dan pengamat dapat menentukan atribut peristiwa OnChange untuk menangani penjadwalan. Kodenya adalah sebagai berikut:
jenis
TSubjek = kelas (TObject)
pribadi
Server FO: TList;
terlindung
» prosedur Perubahan; {Panggil metode ini untuk mengirimkan pemberitahuan}
publik
prosedur RegisterObserver(Pengamat: TSubjectObserver);
prosedur UnregisterObserver(Pengamat: TSubjectObserver);
akhir;
TSubjectObserver = kelas (TComponent)
pribadi
Diaktifkan: Boolean;
» FOnChange: TNotifyEvent;
terlindung
» Perubahan Prosedur;
diterbitkan
properti Diaktifkan: Boolean baca FEnabled tulis FEnabled;
» properti OnChange: TNotifyEvent baca FOnChange tulis FOnChange;
akhir;
pelaksanaan
prosedurTSubjek.Ubah;
var
» Obs: TSubjectObserver;
»Saya: Bilangan Bulat;
mulai
» untuk I := 0 hingga FObservers.Count - 1 lakukan
" mulai
» Obs := FObserver[I];
» jika Obs.Enabled maka Obs.Change;
" akhir;
akhir;
prosedur TSubject.RegisterObserver(Pengamat: TSubjectObserver);
mulai
jika FObservers.IndexOf(Observer) = -1 maka
FObservers.Add(Pengamat);
akhir;
prosedur TSubject.UnregisterObserver(Pengamat: TSubjectObserver);
mulai
FObservers.Hapus(Pengamat);
akhir;
procedureTSubjectObserver.Ubah;
mulai
» jika Ditugaskan(FOnChange) maka FOnChange(Self);
akhir;
Dalam kode implementasi di atas:
? Metode Perubahan pada Tsubject melakukan iterasi melalui semua pengamat yang terdaftar dan memanggil metode Perubahan pada setiap pengamat, yang merupakan implementasi dari pemberitahuan satu-ke-banyak.
? Properti Enabled dari pengamat menentukan apakah ia menerima atau menerima notifikasi
? Acara OnChange dari TsubjectObserver sebenarnya menangani sinkronisasi dan operasi lainnya.
Pengorganisasian
//Banyak kutipan dari "Pola Desain"