Arayüz Tasarımı
Coddy'nin Python Journey'sinin Nesne Yönelimli Programlama bölümünün bir parçası. Ders 26 / 64.
Bir arayüz, sınıfların uyması gereken bir sözleşme tanımlar. Python'da, tüm metotların soyut olduğu soyut temel sınıfları kullanarak arayüzler oluştururuz.
abc modülünü içe aktarın:
from abc import ABC, abstractmethodYalnızca soyut metotlardan oluşan bir arayüz oluşturun:
class Drawable(ABC):
@abstractmethod
def draw(self):
pass
@abstractmethod
def resize(self, width, height):
passBir arayüzdeki tüm metotlar soyut olmalıdır; gerçekleştiren sınıfların ne yapması gerektiğini tanımlarlar, bunu nasıl yapacaklarını değil.
Arayüzü somut bir sınıfta uygulayın:
class Circle(Drawable):
def __init__(self, radius):
self.radius = radius
def draw(self):
return "Drawing a circle"
def resize(self, width, height):
self.radius = min(width, height) / 2
return f"Resized circle to radius {self.radius}"Aynı arayüzü uygulayan başka bir sınıf oluşturun:
class Rectangle(Drawable):
def __init__(self, width, height):
self.width = width
self.height = height
def draw(self):
return "Drawing a rectangle"
def resize(self, width, height):
self.width = width
self.height = height
return f"Resized rectangle to {width}x{height}"Arayüzü polimorfik olarak kullanın:
shapes = [Circle(5), Rectangle(3, 4)]
for shape in shapes:
print(shape.draw())
print(shape.resize(10, 8))Çıktı:
Drawing a circle
Resized circle to radius 4.0
Drawing a rectangle
Resized rectangle to 10x8Arayüzleri tür ipuçları olarak da kullanabilirsiniz:
def render_shape(drawable: Drawable):
return drawable.draw()
circle = Circle(3)
print(render_shape(circle))Çıktı:
Drawing a circleTemel Nokta: Arayüzler, sınıfların bunu nasıl yapacağını değil, ne yapması gerektiğini tanımlar. Uygulayan sınıfların uyması gereken açık sözleşmeler oluşturmak için yalnızca soyut metotlar içeren soyut temel sınıfları kullanın. Bu, farklı uygulamalar arasında tutarlı davranış sağlar.
Görev
OrtaBu görevde, arayüzlere sahip bir medya oynatıcı sistemi uygulayacaksınız.
Aşağıdaki dosyaları düzenlemeniz gerekiyor:
playable.py- Soyut temel sınıfları (arayüzleri) uygulayınsong.py- Song sınıfını uygulayınvideo.py- Video sınıfını uygulayınmediaplayer.py- MediaPlayer sınıfını uygulayın
Her dosyada, uygulamanıza rehberlik edecek ayrıntılı TODO yorumları bulunur. Uygun kalıtım ve arayüz uygulamasıyla eksiksiz bir medya oynatıcı sistemi oluşturmak için bu yorumları izleyin.
Kendin dene
from song import Song
from video import Video
from mediaplayer import MediaPlayer
from playable import Playable, MediaInfo
# Kapsamlı test durumu işleyicisi
test_case = input()
if test_case == "default_test":
# Orijinal problemden varsayılan test durumu
song = Song("Bohemian Rhapsody", "Queen", 355)
video = Video("Python Tutorial", "1080p", 1800)
player = MediaPlayer()
# Şarkı ile test
player.set_media(song)
print(player.current_media.get_info())
print(player.play())
print(player.pause())
print(player.stop())
print() # Okunabilirlik için boş satır
# Video ile test
player.set_media(video)
print(player.current_media.get_info())
print(player.play())
print(player.pause())
print(player.stop())
elif test_case == "empty_player":
# Medya ayarlanmamış medya oynatıcıyı test et
player = MediaPlayer()
print(player.play()) # Should print "No media set"
print(player.pause()) # Should print "No media set"
print(player.stop()) # Should print "No media set"
elif test_case == "time_formatting":
# get_info() metodundaki zaman biçimlendirmesini test et
song1 = Song("Short Song", "Artist A", 65) # 1:05
song2 = Song("Long Song", "Artist B", 3661) # 61:01
video1 = Video("Hour Video", "720p", 3600) # 60:00
print(song1.get_info())
print(song2.get_info())
print(video1.get_info())
elif test_case == "interface_compliance":
# Song ve Video'nun arayüzleri düzgün şekilde uyguladığını test et
song = Song("Test Song", "Test Artist", 180)
video = Video("Test Video", "480p", 240)
# Arayüz uygulamasını kontrol et
print(f"Song implements Playable: {isinstance(song, Playable)}")
print(f"Song implements MediaInfo: {isinstance(song, MediaInfo)}")
print(f"Video implements Playable: {isinstance(video, Playable)}")
print(f"Video implements MediaInfo: {isinstance(video, MediaInfo)}")
# Tüm arayüz metotlarını test et
print(song.play())
print(song.pause())
print(song.stop())
print(song.get_title())
print(song.get_duration())
print(song.get_info())
print(video.play())
print(video.pause())
print(video.stop())
print(video.get_title())
print(video.get_duration())
print(video.get_info())
elif test_case == "polymorphism":
# Farklı medya türlerinden oluşan bir liste ile polimorfik davranışı test et
media_list = [
Song("Song 1", "Artist 1", 180),
Video("Video 1", "720p", 300),
Song("Song 2", "Artist 2", 240),
Video("Video 2", "1080p", 420)
]
player = MediaPlayer()
for media in media_list:
player.set_media(media)
print(f"Media: {media.get_title()}")
print(f"Info: {media.get_info()}")
print(f"Play: {player.play()}")
print()
elif test_case == "edge_cases":
# Uç durumları test et
empty_song = Song("", "", 0)
edge_video = Video("A" * 100, "", -10) # Çok uzun başlık, boş çözünürlük, negatif süre
print(f"Empty song info: {empty_song.get_info()}")
print(f"Edge video info: {edge_video.get_info()}")
player = MediaPlayer()
player.set_media(empty_song)
print(player.play())
player.set_media(edge_video)
print(player.play())
elif test_case == "stress_test":
# Birçok medya nesnesiyle bir stres testi uygula
songs = [Song(f"Song {i}", f"Artist {i}", i * 30) for i in range(1, 101)]
videos = [Video(f"Video {i}", f"{i*10}p", i * 60) for i in range(1, 101)]
player = MediaPlayer()
# Tüm şarkılarla test et
for i, song in enumerate(songs):
player.set_media(song)
if i % 10 == 0: # Çok fazla çıktıyı önlemek için yalnızca her 10.'yu yazdır
print(f"Playing song {i+1}: {player.play()}")
# Tüm videolarla test et
for i, video in enumerate(videos):
player.set_media(video)
if i % 10 == 0: # Çok fazla çıktıyı önlemek için yalnızca her 10.'yu yazdır
print(f"Playing video {i+1}: {player.play()}")
print("Stress test completed successfully!")Bu ders kısa bir quiz içerir. Soruları yanıtlamak ve ilerlemeni kaydetmek için derse başla.
Nesne Yönelimli Programlama 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ıKendi başına pratik yap: Online Python derleyicisi