Masalah
Saya sedang mengerjakan proyek Python yang kelas utamanya sedikit " God Object ". Ada begitu banyak atribut dan metode!
Saya ingin memperbaiki kelas.
Sejauh ini…
Untuk langkah pertama, saya ingin melakukan sesuatu yang relatif sederhana; tetapi ketika saya mencoba pendekatan yang paling mudah, itu memecahkan beberapa tes dan contoh yang ada.
Pada dasarnya, kelas memiliki daftar atribut yang sangat panjang — tetapi saya dapat dengan jelas melihat mereka dan berpikir, “5 atribut ini terkait ... 8 ini juga terkait… dan kemudian ada sisanya.”
getattr
Saya pada dasarnya hanya ingin mengelompokkan atribut terkait ke dalam kelas pembantu seperti dikt. Saya punya perasaan __getattr__
akan ideal untuk pekerjaan itu. Jadi saya memindahkan atribut ke kelas yang terpisah, dan, tentu saja, __getattr__
bekerja dengan sangat baik…
Pada awalnya .
Tetapi kemudian saya mencoba menjalankan salah satu contoh. Contoh subclass mencoba mengatur salah satu dari atribut ini secara langsung (di tingkat kelas ). Tetapi karena atribut tidak lagi "secara fisik terletak" di kelas induk, saya mendapat kesalahan mengatakan bahwa atribut tidak ada.
@Properti
Saya kemudian membaca tentang @property
dekorator. Tetapi kemudian saya juga membaca bahwa itu menciptakan masalah untuk subclass yang ingin dilakukan self.x = blah
ketika x
merupakan properti dari kelas induk.
Diinginkan
- Biarkan semua kode klien terus bekerja menggunakan
self.whatever
, bahkan jikawhatever
properti orangtua tidak "secara fisik terletak" di kelas (atau contoh) itu sendiri. - Kelompokkan atribut terkait ke dalam wadah mirip-dikt.
- Mengurangi kebisingan ekstrim dari kode di kelas utama.
Misalnya, saya tidak hanya ingin mengubah ini:
larry = 2
curly = 'abcd'
moe = self.doh()
Ke dalam ini:
larry = something_else('larry')
curly = something_else('curly')
moe = yet_another_thing.moe()
... karena itu masih berisik. Meskipun itu berhasil membuat atribut hanya menjadi sesuatu yang dapat mengelola data, yang asli memiliki 3 variabel dan versi tweak masih memiliki 3 variabel.
Namun, saya akan baik-baik saja dengan sesuatu seperti ini:
stooges = Stooges()
Dan jika pencarian self.larry
gagal, sesuatu akan memeriksa stooges
dan melihat apakah larry
ada. (Tetapi itu juga harus bekerja jika subclass mencoba melakukannya larry = 'blah'
di tingkat kelas.)
Ringkasan
- Ingin mengganti grup atribut terkait di kelas induk dengan satu atribut yang menyimpan semua data di tempat lain
- Ingin bekerja dengan kode klien yang ada yang menggunakan (misalnya)
larry = 'blah'
di tingkat kelas - Ingin terus mengizinkan subclass untuk memperluas, menimpa, dan memodifikasi atribut-atribut yang dire-refaktasi ini tanpa mengetahui ada yang berubah
Apakah ini mungkin? Atau saya menggonggong pohon yang salah?