{"id":533,"date":"2017-04-12T19:38:11","date_gmt":"2017-04-12T22:38:11","guid":{"rendered":"http:\/\/gianfratti.com\/?p=533"},"modified":"2017-04-12T19:53:56","modified_gmt":"2017-04-12T22:53:56","slug":"orientacao-a-objetos-a-diferenca-entre-classes-abstratas-e-interfaces","status":"publish","type":"post","link":"http:\/\/gianfratti.com\/index.php\/orientacao-a-objetos-a-diferenca-entre-classes-abstratas-e-interfaces\/","title":{"rendered":"Orienta\u00e7\u00e3o a objetos \u2013 A diferen\u00e7a entre classes abstratas e interfaces"},"content":{"rendered":"<p>Vamos entender um pouco sobre a diferen\u00e7a entre classes abstratas e interfaces.<\/p>\n<p>S\u00e3o comuns os questionamentos: Quando devo usar uma classe abstrata? Quando devo usar uma Interface? Devo usar as duas?<\/p>\n<p>Na verdade, uma Classe Abstrata sem qualquer implementa\u00e7\u00e3o, tem o aspect parecido com uma Interface. Mas ambas possuem v\u00e1rias diferen\u00e7as e similaridades entre si. Pensando neste tipo de d\u00favida, este pequeno artigo tenta elucidar algumas quest\u00f5es.<!--more--><\/p>\n<h3>Interfaces<\/h3>\n<p>Vamos come\u00e7ar com as interfaces, j\u00e1 t\u00e3o faladas em outros artigos. Uma interface nada mais \u00e9 que um conjunto de declara\u00e7\u00f5es de m\u00e9todos o qual a implementa\u00e7\u00e3o \u00e9 obrigat\u00f3ria para todas as classes que implementam a interface.<\/p>\n<p>Eu j\u00e1 li em v\u00e1rios lugares que a interface pode ser pensada como um contrato, e a analogia faz sentido. Um contrato apresenta clausulas que precisam ser cumpridas. Uma classe que implementa uma interface precisa ter todos os m\u00e9todos que foram declarados na interface.<\/p>\n<p>Por exemplo se temos a interface <strong>ITeste<\/strong>:<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\npublic interface ITeste\r\n{\r\n    void Metodo1();\r\n    int Metodo2(int i, int j);\r\n}\r\n\r\n<\/pre>\n<p>Se a classe <strong>Teste<\/strong> implementar a interface <strong>ITeste<\/strong>, n\u00e3o h\u00e1 alternativa, a classe <strong>Teste<\/strong> precisa ter os dois m\u00e9todos declarados na interface. E como voc\u00ea pode perceber, os m\u00e9todos da interface s\u00e3o p\u00fablicos. E isso faz todo o sentido, j\u00e1 que todo o programa sabe que esta classe implementa a interface \u2013 ou seja, esta classe tem os m\u00e9todos em quest\u00e3o.<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\nclass Teste : ITeste\r\n{\r\n    public void Metodo1()\r\n    {\r\n    }\r\n\r\n    public int Metodo2(int i, int j)\r\n    {\r\n        return 0;\r\n    }\r\n}\r\n<\/pre>\n<p>Uma vantagem das interfaces \u00e9 que ela permite que classes que n\u00e3o tem rela\u00e7\u00e3o l\u00f3gica alguma possam ser \u2018agrupadas\u2019. Por exemplo, vamos imaginar a interface <strong>ILog<\/strong>, que serve para escrever mensagens num log, como abaixo:<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\npublic interface ILog\r\n{\r\n    void EscreveLog(string mensagem);\r\n}\r\n<\/pre>\n<p>Podemos ent\u00e3o fazer as classes <strong>LogTxt<\/strong> e <strong>LogXml<\/strong> (ambas implementando <strong>ILog<\/strong>).<br \/>\nEstas classes n\u00e3o t\u00eam rela\u00e7\u00e3o entre si (cada uma lida com a escrita de log de sua forma), mas a interface as \u2018agrupa\u2019.<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\nclass LogTxt : ILog\r\n{\r\n    public void EscreveLog(string mensagem)\r\n    {\r\n        \/\/ logica para log num txt\r\n    }\r\n}\r\nclass LogXml : ILog\r\n{\r\n    public void EscreveLog(string mensagem)\r\n    {\r\n        \/\/ logica para log num xml\r\n    }\r\n}\r\n<\/pre>\n<p>Tanto que qualquer m\u00e9todo que precisa escrever algum log pode ter um <strong>ILog<\/strong> como par\u00e2metro. Da\u00ed voc\u00ea pode passar qualquer classe que implemente <strong>ILog<\/strong> (e nem importa se o m\u00e9todo <strong>EscreveLog<\/strong> realmente funcione, desde que esteja implementado).<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\npublic void MetodoExemplo(ILog log)\r\n{\r\n    log.EscreveLog(&quot;&quot;);\r\n}\r\n<\/pre>\n<h3>Classes abstratas<\/h3>\n<p>Classes abstratas podem ser pensadas como interfaces com mais recursos. Antes de mais nada, uma classe abstrata <strong>\u00e9 uma classe<\/strong> \u2013 sim parece \u00f3bvio, mas lembre-se que uma classe tem m\u00e9todos (e n\u00e3o apenas assinaturas de m\u00e9todos) e vari\u00e1veis.<\/p>\n<p>Por exemplo, pense na classe abstrata <strong>ClasseTesteAbstract<\/strong>. Ela tem vari\u00e1veis internas e dois m\u00e9todos <strong>Protected<\/strong>. Note que os m\u00e9todos j\u00e1 apresentam programa\u00e7\u00e3o, o que n\u00e3o \u00e9 poss\u00edvel numa interface.<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\npublic abstract class ClasseTesteAbstract\r\n{\r\n    public int i1;\r\n    public double d3;\r\n\r\n    public int Metodo1(int i)\r\n    {\r\n        return -i;\r\n    }\r\n\r\n    public double Metodo2(double d1, double d2)\r\n    {\r\n        return d1*d2;\r\n    }\r\n}\r\n<\/pre>\n<p>Classes abstratas s\u00e3o <strong>abstratas<\/strong> porque n\u00e3o podem ser instanciadas. Ent\u00e3o a linha de c\u00f3digo abaixo <strong>n\u00e3o pode ser feita<\/strong>.<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\nvar teste = new ClasseTesteAbstract(); \/\/ errado e imposs\u00edvel\r\n<\/pre>\n<p>O que precisamos fazer \u00e9 usar o recurso de heran\u00e7a das linguagens orientadas a objetos. Vamos criar a <strong>SubclasseTeste<\/strong> que herda de <strong>ClasseTesteAbstract<\/strong>. Note que n\u00e3o adicionamos nenhum c\u00f3digo na classe, porque ele j\u00e1 herdou todo o c\u00f3digo da <strong>ClasseTesteAbstract<\/strong>.<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\npublic class SubclasseTeste : ClasseTesteAbstract\r\n{\r\n\r\n}\r\n<\/pre>\n<p>Com isso, conseguimos fazer algo assim:<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\nvar subc = new SubclasseTeste();\r\nsubc.Metodo1(18);\r\nsubc.Metodo2(5.5, 6.6);\r\nvar valor_inteiro = subc.i1;\r\nvar valor_double = subc.d3;\r\n<\/pre>\n<p>Ou seja, a classe abstrata pode impor a programa\u00e7\u00e3o de m\u00e9todos \u2013 e, atrav\u00e9s do recurso de sobrecarga, uma subclasse pode cancelar esta imposi\u00e7\u00e3o ou trabalhar por cima dela (mas isto \u00e9 assunto para outro artigo).<\/p>\n<p>Numa primeira an\u00e1lise, pode parecer que classes abstratas s\u00e3o melhores que interfaces, mas se voltarmos ao exemplo das interfaces (com as classes <strong>LogTxt<\/strong> e <strong>LogXml<\/strong>), uma classe abstrata n\u00e3o ajudaria em nada neste caso, pois n\u00e3o faria sentido a imposi\u00e7\u00e3o de um c\u00f3digo sendo que cada classe tem sua pr\u00f3pria programa\u00e7\u00e3o.<\/p>\n<p>Ent\u00e3o o fator determinante para o uso de interfaces ou de classes abstratas \u00e9 a imposi\u00e7\u00e3o da programa\u00e7\u00e3o dos m\u00e9todos. Ora. se v\u00e1rias classes apresentam m\u00e9todos com a mesma programa\u00e7\u00e3o base, provavelmente vale a pena usar uma classe abstrata para diminuir a repeti\u00e7\u00e3o de c\u00f3digo (ali\u00e1s, esta \u00e9 uma das v\u00e1rias vantagens da orienta\u00e7\u00e3o a objetos).<\/p>\n<p>Interfaces, por outro lado, tem o objetivo de garantir que diferentes classes, que n\u00e3o t\u00eam nenhuma rela\u00e7\u00e3o entre si, apresentem o mesmo conjunto b\u00e1sico de m\u00e9todos. Uma abordagem n\u00e3o substitui a outra, muito pelo contr\u00e1rio \u2013 o que voc\u00ea mais encontra s\u00e3o classes do .NET (por exemplo) que herdam de outra classe e implementam uma ou mais interfaces.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Vamos entender um pouco sobre a diferen\u00e7a entre classes abstratas e interfaces. <span class=\"ellipsis\">&hellip;<\/span> <span class=\"more-link-wrap\"><a href=\"http:\/\/gianfratti.com\/index.php\/orientacao-a-objetos-a-diferenca-entre-classes-abstratas-e-interfaces\/\" class=\"more-link\"><span>Read More &rarr;<\/span><\/a><\/span><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_exactmetrics_skip_tracking":false,"_exactmetrics_sitenote_active":false,"_exactmetrics_sitenote_note":"","_exactmetrics_sitenote_category":0,"_jetpack_memberships_contains_paid_content":false,"footnotes":""},"categories":[2],"tags":[],"class_list":["post-533","post","type-post","status-publish","format-standard","hentry","category-net-framework"],"jetpack_featured_media_url":"","jetpack_sharing_enabled":true,"_links":{"self":[{"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/posts\/533","targetHints":{"allow":["GET"]}}],"collection":[{"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/comments?post=533"}],"version-history":[{"count":8,"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/posts\/533\/revisions"}],"predecessor-version":[{"id":541,"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/posts\/533\/revisions\/541"}],"wp:attachment":[{"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/media?parent=533"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/categories?post=533"},{"taxonomy":"post_tag","embeddable":true,"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/tags?post=533"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}