İleri Seviye Property Dekoratörleri
Coddy'nin Python Journey'sinin Object Oriented Programming bölümünün bir parçası — ders 31 / 64.
Gelişmiş özellik dekoratörleri; hesaplanmış özellikler, silici metotlar ve tam özellik yönetimi dahil olmak üzere öznitelik erişimi üzerinde daha gelişmiş kontrol sağlar.
İşte diğer özniteliklerden değerler türeten hesaplanmış özelliklere (computed properties) bir örnek:
class Rectangle:
def __init__(self, width, height):
self.width = width
self.height = height
@property
def area(self):
return self.width * self.height
@property
def perimeter(self):
return 2 * (self.width + self.height)Hesaplanmış özellikleri normal öznitelikler gibi kullanın:
rect = Rectangle(5, 3)
print(rect.area) # 15 - otomatik olarak hesaplandı
print(rect.perimeter) # 16 - otomatik olarak hesaplandıGetter (alıcı), setter (ayarlayıcı) ve deleter (silici) özelliklerine sahip bir özellik (property) oluşturun:
class Temperature:
def __init__(self):
self._temp = 0
@property
def temperature(self):
return self._temp
@temperature.setter
def temperature(self, value):
if value < -273.15:
raise ValueError("Temperature below absolute zero!")
self._temp = value
@temperature.deleter
def temperature(self):
print("Resetting temperature to 0")
self._temp = 0Tam özellik işlevselliğini kullanın:
temp = Temperature()Doğrulama içeren ayarlayıcıyı (setter) kullanın:
temp.temperature = 25
print(temp.temperature) # 25
# temp.temperature = -300 # ValueError hatası fırlatırSiliciyi kullanın:
del temp.temperature
print(temp.temperature) # 0Bir oyun puanı ile daha karmaşık bir örnek oluşturalım:
class Player:
def __init__(self, name):
self.name = name
self._score = 0
self._level = 1
@property
def score(self):
return self._score
@score.setter
def score(self, value):
if value >= 0:
self._score = value
self._level = (value // 1000) + 1
else:
raise ValueError("Score cannot be negative")
@score.deleter
def score(self):
print(f"Resetting {self.name}'s progress")
self._score = 0
self._level = 1
@property
def level(self):
return self._level
player = Player("Alice")
player.score = 2500
print(f"Score: {player.score}, Level: {player.level}") # Score: 2500, Level: 3
del player.score
print(f"Score: {player.score}, Level: {player.level}") # Score: 0, Level: 1Çıktı:
15
16
25
Resetting temperature to 0
0
Score: 2500, Level: 3
Resetting Alice's progress
Score: 0, Level: 1Anahtar Nokta: Gelişmiş özellik dekoratörleri (property decorators); hesaplanmış özelliklere (diğer verilerden hesaplanan), @property.deleter ile özellik silmeye ve öznitelikleri alma, ayarlama ve silme üzerinde tam kontrole olanak tanır. Bu, güçlü veri doğrulama ve kapsüllemeyi (encapsulation) korurken sezgisel arayüzler oluşturur.
Görev
OrtaBu challenge'da, uygun kapsülleme (encapsulation) ve özellik doğrulaması (property validation) içeren bir Rectangle sınıfı uygulayacaksınız.
rectangle.py- Düzenlemeniz gereken dosyadır, uygulamanıza rehberlik edecek TODO yorumlarını içerirdriver.py- Kapsamlı test senaryolarını içerir (değiştirmeyin)
_widthve_heightiçin özel (private) öznitelikler uygulayın- Doğrulama içeren (pozitif olmalı)
widthveheightözellikleri oluşturun- TODO'larda belirtilen uygun ValueError mesajlarını fırlatın
- Önemli: Değerin 0'a eşit veya daha küçük olup olmadığını kontrol edin, ardından hatayı fırlatın (bu, tutarlı bir davranış sağlar)
areaveperimeteriçin salt okunur (read-only) özellikler uygulayın- TODO'larda açıklandığı gibi getter, setter ve deleter işlevselliğine sahip bir
dimensionsözelliği oluşturun- Önemli: Setter içinde demet açma (tuple unpacking) sözdizimini kullanın:
width, height = dimensions
- Önemli: Setter içinde demet açma (tuple unpacking) sözdizimini kullanın:
Kopya kağıdı
Gelişmiş özellik dekoratörleri (property decorators), hesaplanmış özellikler, siliciler (deleters) ve tam özellik yönetimi ile öznitelik erişimi üzerinde gelişmiş kontrol sağlar.
Hesaplanmış Özellikler:
class Rectangle:
def __init__(self, width, height):
self.width = width
self.height = height
@property
def area(self):
return self.width * self.height
@property
def perimeter(self):
return 2 * (self.width + self.height)Getter, Setter ve Deleter ile Tam Özellik:
class Temperature:
def __init__(self):
self._temp = 0
@property
def temperature(self):
return self._temp
@temperature.setter
def temperature(self, value):
if value < -273.15:
raise ValueError("Temperature below absolute zero!")
self._temp = value
@temperature.deleter
def temperature(self):
print("Resetting temperature to 0")
self._temp = 0Kullanım:
# Hesaplanmış özellikler
rect = Rectangle(5, 3)
print(rect.area) # 15
print(rect.perimeter) # 16
# Tam özellik işlevselliği
temp = Temperature()
temp.temperature = 25 # Setter kullanır
print(temp.temperature) # Getter kullanır
del temp.temperature # Deleter kullanırKendin dene
from rectangle import Rectangle
# Test durumu işleyicisi
test_case = input()
# Temel işlevsellik testi
if test_case == "default_test":
rect = Rectangle(5, 3)
print(f"Width: {rect.width}, Height: {rect.height}")
print(f"Area: {rect.area}, Perimeter: {rect.perimeter}")
# Boyutlar (dimensions) özelliğini test et
print(f"Dimensions: {rect.dimensions}")
rect.dimensions = (10, 8)
print(f"New area: {rect.area}")
# Doğrulamayı test et
try:
rect.width = -2
except ValueError as e:
print(f"Validation error: {e}")
# Siliciyi (deleter) test et
del rect.dimensions
print(f"After reset: {rect.dimensions}")
# Sıfır değerleri ile test
elif test_case == "zero_values":
try:
rect = Rectangle(0, 5)
except ValueError as e:
print(f"Error creating rectangle: {e}")
try:
rect = Rectangle(5, 0)
except ValueError as e:
print(f"Error creating rectangle: {e}")
# Negatif değerler ile test
elif test_case == "negative_values":
rect = Rectangle(5, 3)
original_dimensions = rect.dimensions
try:
rect.dimensions = (5, -3)
except ValueError as e:
print(f"Error setting dimensions: {e}")
print(f"Dimensions after failed update: {rect.dimensions}")
print(f"Original dimensions preserved: {rect.dimensions == original_dimensions}")
# Büyük değerler ile test
elif test_case == "large_values":
rect = Rectangle(1000000, 2000000)
print(f"Large rectangle area: {rect.area}")
print(f"Large rectangle perimeter: {rect.perimeter}")
# Ondalıklı (float) değerler ile test
elif test_case == "float_values":
rect = Rectangle(3.5, 2.75)
print(f"Dimensions: {rect.dimensions}")
print(f"Area: {rect.area}")
print(f"Perimeter: {rect.perimeter}")
rect.dimensions = (1.1, 2.2)
print(f"New area with float dimensions: {rect.area}")
# Tip hataları ile test
elif test_case == "type_errors":
try:
rect = Rectangle("5", 3)
except Exception as e:
print(f"Type error during creation: {type(e).__name__}: {e}")
rect = Rectangle(5, 3)
try:
rect.dimensions = 10 # Bir demet (tuple) değil
except Exception as e:
print(f"Type error setting dimensions: {type(e).__name__}: {e}")
# Çoklu özellik işlemleri testi
elif test_case == "property_operations":
rect = Rectangle(5, 10)
print(f"Initial - Width: {rect.width}, Height: {rect.height}, Area: {rect.area}")
rect.width = 8
print(f"After width change - Width: {rect.width}, Area: {rect.area}")
rect.height = 6
print(f"After height change - Height: {rect.height}, Area: {rect.area}")
rect.dimensions = (12, 9)
print(f"After dimensions change - Dimensions: {rect.dimensions}, Area: {rect.area}")
del rect.dimensions
print(f"After reset - Dimensions: {rect.dimensions}, Area: {rect.area}")
# Özellik doğrulama sınır durumları testi
elif test_case == "validation_edge_cases":
rect = Rectangle(5, 3)
try:
rect.width = 0
except ValueError as e:
print(f"Zero width error: {e}")
# Çok küçük pozitif değer kabul edilmelidir
rect.height = 0.0001
print(f"Small height accepted: {rect.height}")
print(f"Area with small height: {rect.area}")
# Çoklu dikdörtgen testi
elif test_case == "multiple_rectangles":
rect1 = Rectangle(5, 3)
rect2 = Rectangle(10, 2)
rect3 = Rectangle(4, 4)
print(f"Rectangle 1 - Area: {rect1.area}, Perimeter: {rect1.perimeter}")
print(f"Rectangle 2 - Area: {rect2.area}, Perimeter: {rect2.perimeter}")
print(f"Rectangle 3 - Area: {rect3.area}, Perimeter: {rect3.perimeter}")
# Her bir dikdörtgeni değiştir
rect1.width = 7
rect2.height = 5
rect3.dimensions = (6, 6)
print(f"After modifications:")
print(f"Rectangle 1 - Dimensions: {rect1.dimensions}")
print(f"Rectangle 2 - Dimensions: {rect2.dimensions}")
print(f"Rectangle 3 - Dimensions: {rect3.dimensions}")
# Birçok işlem ile performans testi
elif test_case == "performance_test":
rect = Rectangle(5, 5)
# Birçok özellik işlemi gerçekleştir
for i in range(1000):
rect.width = i % 10 + 1 # 1-10 arası değerler
rect.height = i % 5 + 1 # 1-5 arası değerler
area = rect.area # Hesaplanmış özelliğe eriş
perimeter = rect.perimeter # Hesaplanmış özelliğe eriş
dims = rect.dimensions # Özellik alıcısına (getter) eriş
print(f"Final state after 1000 operations:")
print(f"Width: {rect.width}, Height: {rect.height}")
print(f"Area: {rect.area}, Perimeter: {rect.perimeter}")Bu ders kısa bir quiz içerir. Soruları yanıtlamak ve ilerlemeni kaydetmek için derse başla.
Object Oriented Programming bölümündeki tüm dersler
1OOP Temelleri
Harici DosyalarOOP'ye GirişSınıflar ve Nesnelerself ParametresiMetotlarÖzniteliklerYapıcı Metot (__init__)Özet - Basit Hesap Makinesi4Kalıtım
Temel Kalıtımsuper() FonksiyonuMetot Geçersiz KılmaÇoklu KalıtımMetot Çözümleme SırasıÖzet - Çalışan Hiyerarşisi7Özel Metotlar
Sihirli Metotlara GirişOperatör Aşırı YüklemeKapsayıcı Sihirli MetotlarıÖzet - Özel Liste10Tasarım Kalıpları Bölüm 1
Tasarım kalıplarına girişSingleton KalıbıFactory KalıbıObserver KalıbıStrategy Kalıbı13Final Meydan Okumaları
E-öğrenme PlatformuBankacılık SistemiOyun Karakteri GeliştirmeAraç Kiralama Servisi5Çok Biçimlilik (Polymorphism)
Metot Geçersiz Kılmaya Yeniden BakışDuck TypingSoyut Sınıflar ve MetotlarArayüz TasarımıÖzet - Şekil Hesaplayıcı8İleri Düzey OOP Kavramları
Kompozisyon ve KalıtımMixinsStatik ve Sınıf MetotlarıSınıf DekoratörleriBağlam Yöneticileri11Tasarım Kalıpları Bölüm 2
Komut KalıbıAdaptör KalıbıDekoratör KalıbıŞablon Metot KalıbıDurum KalıbıKompozit Kalıbı3Sınıf Özellikleri
Örnek ve Sınıf DeğişkenleriProperty DekoratörleriGizli ÖzniteliklerÖzet - Banka Hesabı Yöneticisi6Kapsülleme
Public, Protected, Private ÜyelerErişim BelirleyicilerBilgi Gizlemeİleri Seviye Property DekoratörleriÖzet - Öğrenci Kayıt Sistemi