Design Patterns - Parte 2 - Artigo .Net Magazine 48
Neste artigo vamos abordar dois padrões: Template Method e Decorator.
No primeiro artigo desta série vimos o que são design patterns e porque utilizá-los. Vimos também um dos padrões mais importantes e também um dos mais simples: o padrão Strategy e o aplicamos a um exemplo real. Neste artigo vamos abordar dois padrões não menos importantes: Template Method e Decorator.
O padrão Template Method vai nos ajudar a garantir que os desenvolvedores trabalhando em uma aplicação (muitas vezes nós mesmos) não esqueçam nenhum passo de determinada operação através do encapsulamento de um algoritmo. Já o padrão Decorator vai nos mostrar como compor algoritmos de forma que possamos acumular comportamentos.
Relembrando o Strategy
Vimos no artigo anterior que é importante encapsular o que muda. Foi o que fizemos quando percebemos que o cálculo de impostos mudaria de acordo com diversas regras e o separamos do método de fechar uma nota fiscal (NF). Encapsular é algo muito interessante, soa bonito, e as pessoas se interessam quando falamos nisso, então vamos explorar essa ideia um pouco mais.
Veja na Listagem 1 o código base da classe de NFs, de interface e suas implementações, onde o padrão Strategy foi aplicado (ligeiramente modificado desde o último artigo). A Figura 1 mostra o diagrama de classes.
'classe base, com o padrão Strategy aplicado, delegando
'o trabalho de cálculo de imposto à interface IInfoImposto
Public MustInherit Class NFSemDP
Protected _Imposto As IInfoImposto
Private _decTotalNF, _decTotalImpostos As Decimal
Private _blnFechada As Boolean = False
Public Property Imposto() As IInfoImposto
Get
Return _Imposto
End Get
Set(ByVal value As IInfoImposto)
_Imposto = value
End Set
End Property
Public Property TotalNF() As Decimal
Get
Return _decTotalNF
End Get
Set(ByVal value As Decimal)
If _blnFechada Then
Throw New Exception("NF Fechada")
End If
_decTotalNF = value
End Set
End Property
Public Property TotalImpostos() As Decimal
Get
Return _decTotalImpostos
End Get
Private Set(ByVal value As Decimal)
_decTotalImpostos = value
End Set
End Property
Public MustOverride ReadOnly Property Local() As String
Public Sub FechaNF()
TotalImpostos = Imposto.CalculaImposto(Me.TotalNF)
_blnFechada = True
End Sub
End Class
'implentação simples da classe de imposto para a cidade de gramado
Public Class NFGramado
Inherits NFSemDP
Public Sub New()
_Imposto = New ImpostoRS
End Sub
Public Overrides ReadOnly Property Local() As String
Get
Return "Gramado"
End Get
End Property
End Class
'interface simples de imposto, apenas com o método de cálculo
Public Interface IInfoImposto
Function CalculaImposto(ByVal decValorNF As Decimal) As Decimal
End Interface
'implementação da classe de impostos para todo o RS, utilizada pela cidade de gramado
Public Class ImpostoRS
Implements IInfoImposto
Public Function CalculaImposto(ByVal decValorNF As Decimal)
As Decimal Implements IInfoImposto.CalculaImposto
Const decAliquotaICMS@ = 0.12D
Const decAliquotaISS@ = 0.03D
Return Decimal.Round(decValorNF * decAliquotaICMS) +
Decimal.Round(decValorNF * decAliquotaISS, 2)
End Function
End
Note que a implementação das classes concretas de cálculo de imposto (ImpostoSP, ImpostoRS e ImpostoBA) pouco importa à classe de imposto e suas herdeiras. Tudo que elas querem é chamar o método CalculaImposto. A classe ImpostoSP é praticamente igual à classe ImpostoRS, mudando apenas as alíquotas, e um imposto a mais (Imposto IXYZ). Veja-a na Listagem 2.
Public Class ImpostoSP
Implements IInfoImposto
Public Function CalculaImposto(ByVal decValorNF As Decimal) As
Decimal Implements IInfoImposto.CalculaImposto
Const decAliquotaICMS@ = 0.18D
Const decAliquotaISS@ = 0.05D
Const decAliquotaIXYZ@ = 0.01D
Return Decimal.Round(decValorNF * decAliquotaICMS) +
Decimal.Round(decValorNF * decAliquotaISS, 2) +
Decimal.Round(decValorNF * decAliquotaIXYZ, 2)
End Function
End Class
Veja agora que a classe ImpostoBA tem 2 métodos a mais, ambos privados e com função de auxiliar no cálculo dos impostos. Diferentemente da classe ImpostoRS e ImpostoSP, ela foi codificada mais explicitamente. Veja sua implementação na Listagem 3.
" [...] continue lendo...Artigos relacionados
-
Artigo
-
Artigo
-
Artigo
-
Artigo
-
Artigo