Sobes.tech
Senior

Vysvětlete princip náhrady Barbary Liskovové.

sobes.tech AI

Odpověď od AI

Pokud je v programu S podtyp T, pak objekty typu T v programu mohou být nahrazeny objekty typu S bez narušení funkčnosti programu.

Klíčové body:

  • Zachování chování: Podtyp by se měl chovat stejně jako jeho základní typ, z pohledu vnějšího pozorovatele.
  • Invariaty: Invariaty základní třídy by měly být zachovány v podtřídách.
  • Postpodmínky: Postpodmínky (podmínky, které musí být pravdivé po provedení metody) podtřídy by měly být stejné nebo silnější než u základní třídy.
  • Prepodmínky: Prepodmínky (podmínky, které musí být pravdivé před provedením metody) podtřídy by měly být stejné nebo slabší než u základní třídy.

Příklad v Pythonu:

class Rectangle:
    def __init__(self, width, height):
        self._width = width
        self._height = height

    def set_width(self, width):
        self._width = width

    def set_height(self, height):
        self._height = height

    def area(self):
        return self._width * self._height

class Square(Rectangle):
    def __init__(self, side):
        super().__init__(side, side)

    def set_width(self, width):
        self._width = width
        self._height = width # Porušení principu: změna šířky mění i výšku

    def set_height(self, height):
        self._width = height # Porušení principu: změna výšky mění i šířku
        self._height = height

# Příklad použití, který porušuje LSP:
def enlarge_rectangle(rectangle):
    rectangle.set_width(rectangle._width + 1)
    rectangle.set_height(rectangle._height + 1)
    return rectangle.area()

rect = Rectangle(2, 3)
print(f"Oblast po enlarge_rectangle(rect): {enlarge_rectangle(rect)}") # Očekáváno 12

square = Square(2)
print(f"Oblast po enlarge_rectangle(square): {enlarge_rectangle(square)}") # Očekáváno 9, ale kvůli set_width/set_height v Square bude 16. Porušení!

Tento princip je důležitý pro zajištění správnosti dědičnosti a polymorfismu, a činí kód spolehlivějším a předvídatelnějším.