Existuje třída HtmlNode
, od které dědí třídy HtmlElement
a HtmlTextNode
.
Takže např. následující HTML kód
<div>
First text
<strong>Foo</strong>
Second text
</div>
Bude reprezentován jako
HtmlElement(div)
HtmlTextNode(First text)
HtmlElement(strong)
HtmlTextNode(Foo)
HtmlTextNode(Second text)
Potřebuji naparsovaný a v pamětí namodelovaný kód vypsat pěkně zformátovaný. Podle Single responsibility principle by třídy HtmlElement a HtmlTextNode neměli vědět, jak se mají vypsat. Měla by tedy existovat nějaká další třída HtmlPrinter
, která by měla metodu void Print(const HtmlNode*) const
. Problém je, že uvnitř této metody by bylo nutné použít dynamic cast, což je v C++ považováno za známku špatného objektového návrhu.
V C++ jsem nikdy neprogramoval, dělám PHP + javu, ale nějak nerozumím tomu, proč by bylo to, že bude ten objekt znát svoji řetězcovou reprezentaci porušením SRP. Jasně, kdyby se i sám vypisoval, pak je to zcela očividné porušení single responsibility. Ale v podstatě to není nic jiného, než kontejner na data, proč by tedy neměl vědět, jak ta data mají vypadat? Třídy podle mě můžou obsahovat metody jako getHash, compareTo nebo toString a za porušení SRP se to nepovažuje. Ale třeba se pletu a dělám to celou dobu blbě.
Každopádně, pokud bych si měl vybrat mezi porušením SRP a dynamic castem, volil bych spíš takovéhle skoro neznatelné porušení SRP. Dynamic cast se totiž hůře refaktoruje a přináší víc "záludných" problémů. Porušení SRP se naproti tomu opravuje celkem jednoduše. Každopádně, nemyslím si, že by popisovaný příklad byl porušením SRp ale samozřejmě neznám kontext, takže se to špatně určuje.