You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
(Colocando a herança múltipla em seu devido lugar):
1425
1427
ele implementa _traits_ ("traços"), uma forma explícita de mixin originada na linguagem Self.
1426
1428
Simionato escreveu, em seu blog, uma longa série de posts sobre herança múltipla em Python, incluindo
1427
1429
https://fpy.li/14-43[_The wonders of cooperative inheritance, or using super in Python 3_]
@@ -1440,7 +1442,7 @@ Grady Booch et al., e o recomendo fortemente como uma introdução geral ao
1440
1442
pensamento orientado a objetos, independente da linguagem de programação. É um
1441
1443
dos raros livros que trata da herança múltipla sem preconceitos.
1442
1444
1443
-
Hoje, mais que nunca, é de bom tom evitar a herança, então cá estão duas
1445
+
Hoje, mais que nunca, aconselha-se evitar a herança. Então cá estão duas
1444
1446
referências sobre como fazer isso. Brandon Rhodes escreveu
1445
1447
https://fpy.li/14-49[_The Composition Over Inheritance Principle_]
1446
1448
(O princípio da composição antes da herança), parte de seu excelente guia
@@ -1462,7 +1464,7 @@ defendem para Python.
1462
1464
[quote, Alan Kay, The Early History of Smalltalk ("Os Primórdios de Smalltalk")]
1463
1465
____
1464
1466
1465
-
[Nós] começamos a defender a ideia de herança como uma maneira de permitir que
1467
+
[...] começamos a defender a ideia de herança como uma maneira de permitir que
1466
1468
iniciantes pudessem construir [algo] a partir de frameworks que só poderiam ser
1467
1469
projetadas por especialistasfootnote:[Alan Kay, _The Early History of Smalltalk_
1468
1470
(Os Promórdios de Smalltalk), na SIGPLAN Not. 28, 3 (março de 1993),
@@ -1475,73 +1477,102 @@ ____
1475
1477
A((("inheritance and subclassing", "Soapbox discussion",
1476
1478
id="IASsoap14")))((("Soapbox sidebars", "multilevel class hierarchies"))) imensa
1477
1479
maioria dos programadores escreve aplicações, não frameworks. Mesmo aqueles que
1478
-
escrevem frameworks provavelmente passam muito (ou a maior parte) de seu tempo
1480
+
escrevem frameworks provavelmente passam boa parte de seu tempo
1479
1481
escrevendo aplicações. Quando escrevemos aplicações, normalmente não precisamos
1480
1482
criar hierarquias de classes. No máximo escrevemos classes que são subclasses de
1481
1483
ABCs ou de outras classes oferecidas pelo framework. Como desenvolvedores de
1482
1484
aplicações, é muito raro precisarmos escrever uma classe que funcionará como
1483
-
superclasse de outra. As classes que escrevemos são, quase sempre, "classes
1484
-
folha" (isto é, folhas na árvore de herança).
1485
+
superclasse de outra. Quase sempre as classes que escrevemos sãoclasses
1486
+
folha: classes concretas sem subclasses.
1485
1487
1486
1488
Se, trabalhando como desenvolvedor de aplicações, você se pegar criando
1487
-
hierarquias de classe de múltiplos níveis, quase certamente uma ou mais das
1488
-
seguintes alternativas se aplica:
1489
+
hierarquias de classe de múltiplos níveis, aposto que está vivendo uma destas
1490
+
situações:
1489
1491
1490
1492
* Você está reinventando a roda. Procure um framework ou biblioteca que forneça
1491
-
componentes que possam ser reutilizados em sua aplicação.
1493
+
componentes você possa reutilizar em sua aplicação.
1492
1494
1493
1495
* Você está usando um framework mal projetado. Procure uma alternativa.
1494
1496
1495
-
* Você está complicando demais o processo. Lembre-se((("KISS principle"))) do
1497
+
* Você está complicando demais. Lembre-se((("KISS principle"))) do
1496
1498
_Princípio KISS_.
1497
1499
1498
1500
* Você ficou entediado programando aplicações e decidiu criar um novo framework.
1499
1501
Parabéns e boa sorte!
1500
1502
1501
-
Também é possível que todas as alternativas acima se apliquem à sua situação:
1503
+
Também é possível que todas as alternativas acima descrevam situação:
1502
1504
você ficou entediado e decidiu reinventar a roda, escrevendo seu próprio
1503
1505
framework mal projetado e excessivamente complexo, e está sendo forçado a
1504
1506
programar classe após classe para resolver problemas triviais. Espero que você
1505
1507
esteja se divertindo, ou pelo menos que esteja sendo pago para fazer isso.
1506
1508
1507
1509
**Tipos embutidos mal-comportados: bug ou _feature_?**
1508
1510
1509
-
Os((("Soapbox sidebars", "trade-offs of built-ins"))) tipos embutidos `dict`, `list`, e `str` são blocos básicos essenciais do próprio Python, então precisam ser rápidos—qualquer problema de desempenho ali teria severos impactos em praticamente todo o resto.
1510
-
É por isso que o CPython adotou atalhos que fazem com que métodos embutidos se comportem mal, ao não cooperarem com os métodos sobrescritos por subclasses.
1511
-
Um caminho possível para sair desse dilema seria oferecer duas implementações para cada um desses tipos: um "interno", otimizado para uso pelo interpretador, e um externo, facilmente extensível.
1512
-
1513
-
Mas isso nós já temos: `UserDict`, `UserList`,
1514
-
e `UserString` não são tão rápidos quanto seus equivalentes embutidos,
1515
-
mas são fáceis de estender.
1516
-
A abordagem pragmática tomada pelo CPython significa que também podemos usar,
1517
-
em nossas próprias aplicações, as implementações altamente otimizadas mas difíceis estender.
1518
-
E isso faz sentido, considerando que não é tão frequente precisarmos de um mapeamento,
1519
-
uma lista ou uma string customizados, mas usamos `dict`, `list`, e `str` diariamente.
1520
-
Só precisamos estar cientes dos compromissos envolvidos.
1521
-
1522
-
1523
-
1524
-
[role="soapbox-title"]
1525
-
Herança através das linguagens
1526
-
1527
-
Alan Kay((("Soapbox sidebars", "inheritance across languages"))) criou o termo "orientado a objetos", e Smalltalk tinha apenas herança simples, apesar de existirem versões com diferentes formas de suporte a herança múltipla, incluindo os dialetos modernos de Smalltalk, Squeak e Pharo, que suportam _traits_ ("traços")—um dispositivo de linguagem que pode substituir classes mixin, mas evita alguns dos problemas da herança múltipla.
1528
-
1529
-
A primeira linguagem popular a implementar herança múltipla foi o {cpp}, e esse recurso foi abusado o suficiente para que o Java—criado para ser um substituto do {cpp}—fosse projetado sem suporte a herança múltipla de implementação (isto é, sem classes mixin). Quer dizer, isso até o Java 8 introduzir os métodos default, que tornam interfaces muito similares às classes abstratas usadas para definir interfaces em {cpp} e em Python.
1530
-
Depois de Java, a linguagem da JVM mais usada é provavelmente o Scala, que implementa _traits_.
1511
+
Os((("Soapbox sidebars", "trade-offs of built-ins"))) tipos embutidos `dict`,
1512
+
`list`, e `str` são blocos básicos essenciais do próprio Python, então precisam
1513
+
ser rápidos—qualquer problema de desempenho ali teria severos impactos em
1514
+
praticamente todo o resto. É por isso que o CPython adotou atalhos que fazem com
1515
+
que muitos métodos embutidos escritos em C se comportem mal, ao não cooperarem
1516
+
com os métodos sobrescritos por subclasses em Python.
1517
+
1518
+
Uma solução para este dilema seria oferecer duas implementações para cada um
1519
+
desses tipos: uma "interno", otimizada para uso pelo interpretador, e uma externa,
1520
+
facilmente extensível.
1521
+
1522
+
Mas veja só, isso nós já temos: `UserDict`, `UserList`, e `UserString` não são
1523
+
tão rápidos quanto seus equivalentes embutidos, mas são fáceis de estender. A
1524
+
abordagem pragmática tomada pelo CPython significa que também podemos usar, em
1525
+
nossas próprias aplicações, as implementações altamente otimizadas mas difíceis
1526
+
estender. E isso faz sentido, considerando que não é tão frequente precisarmos
1527
+
de um mapeamento, uma lista ou uma string customizados, mas usamos `dict`,
1528
+
`list`, e `str` diariamente. Só precisamos estar cientes dos compromissos
1529
+
envolvidos.
1530
+
1531
+
1532
+
**Herança através das linguagens**
1533
+
1534
+
Alan Kay((("Soapbox sidebars", "inheritance across languages"))) criou o termo
1535
+
"orientado a objetos", e Smalltalk tinha apenas herança simples, apesar de
1536
+
existirem versões com diferentes formas de suporte a herança múltipla, incluindo
1537
+
os dialetos modernos de Smalltalk, Squeak e Pharo, que suportam _traits_
1538
+
("traços")—um dispositivo de linguagem que pode substituir classes mixin, mas
1539
+
evita alguns dos problemas da herança múltipla.
1540
+
1541
+
A primeira linguagem popular a implementar herança múltipla foi o {cpp}, e esse
1542
+
recurso foi abusado o suficiente para que o Java—criado para ser um substituto
1543
+
do {cpp}—fosse projetado sem suporte a herança múltipla de implementação (isto
1544
+
é, sem classes mixin). Quer dizer, isso até o Java 8 (e Kotlin) permitir métodos
1545
+
default, que que aproximam suas interfaces do conceito de classes abstratas
1546
+
que temps em Python e {cpp}.
1531
1547
1532
1548
Outras linguagens que suportam _traits_ são versões recentes de PHP e Groovy,
1533
-
bem como Rust e Raku—a linguagem antes conhecida como Perl 6.footnote:[Meu amigo e revisor técnico Leonardo Rochael explica isso melhor do que eu poderia:
1534
-
"A existência continuada junto com o persistente adiamento da chegada do Perl 6 estava drenando a força de vontade da evolução do próprio Perl. Agora o Perl continua a ser desenvolvido como uma linguagem separada (está na versão 5.34), sem a ameaça de ser descontinuada pela linguagem antes conhecida como Perl 6."]
1549
+
bem como Rus, Scala, t e Raku—a linguagem antes conhecida como Perl 6.footnote:[Meu amigo
1550
+
e revisor técnico Leonardo Rochael explica isso melhor do que eu poderia: "A
1551
+
existência continuada junto com o persistente adiamento da chegada do Perl 6
1552
+
estava drenando a força de vontade da evolução do próprio Perl. Agora o Perl
1553
+
continua a ser desenvolvido como uma linguagem separada (está na versão 5.34),
1554
+
sem a ameaça de ser descontinuada pela linguagem antes conhecida como Perl 6."]
1535
1555
Então podemos dizer que _traits_ estão na moda em 2021.
1536
1556
1537
-
Ruby traz uma perspectiva original para a herança múltipla:
1538
-
não a suporta, mas introduz mixins como um recurso explícito da linguagem. Uma classe Ruby pode incluir um módulo em seu corpo, e aí os métodos definidos no módulo se tornam parte da implementação da classe.
1539
-
Essa é uma forma "pura" de mixin, sem herança envolvida, e está claro que uma mixin Ruby não tem qualquer influência sobre o tipo da classe onde ela é usada.
1540
-
Isso oferece os benefícios das mixins, evitando muitos de seus problemas mais comuns.
1541
-
1542
-
Duas novas linguagens orientadas a objetos que estão recebendo muita atenção limitam severamente a herança: Go e Julia.
1543
-
Ambas giram em torno de programar "objetos" implementando "métodos", e suportam https://fpy.li/7b[polimorfismo], mas evitam o termo "classe".
1544
-
1545
-
Go não tem qualquer tipo de herança, mas oferece uma sintaxe que facilita a composição. Julia tem uma hierarquia de tipos, mas subtipos não podem herdar estrutura, apenas comportamentos, e só é permitido criar subtipos de tipos abstratos. Além disso, os métodos de Julia são implementados com despacho múltiplo—uma forma mais avançada do mecanismo que vimos na <<generic_functions_sec>>.((("", startref="IASsoap14")))
1557
+
Ruby traz uma perspectiva original para a herança múltipla: não a suporta, mas
1558
+
introduz mixins como um recurso explícito da linguagem. Uma classe Ruby pode
1559
+
incluir um módulo em seu corpo, e aí os métodos definidos no módulo se tornam
1560
+
parte da implementação da classe. Essa é uma forma "pura" de mixin, sem herança
1561
+
envolvida, e está claro que uma mixin Ruby não tem qualquer influência sobre o
1562
+
tipo da classe onde ela é usada. Isso oferece os benefícios das mixins, evitando
1563
+
muitos de seus problemas mais comuns.
1564
+
1565
+
Duas novas linguagens orientadas a objetos que estão recebendo muita atenção
1566
+
limitam severamente a herança: Go e Julia. Ambas giram em torno de programar
1567
+
"objetos" implementando "métodos", e suportam https://fpy.li/7b[polimorfismo],
1568
+
mas evitam o termo "classe".
1569
+
1570
+
Go não tem qualquer tipo de herança, mas oferece uma sintaxe que facilita a
1571
+
composição de suas interfaces e structs. Julia tem uma hierarquia de tipos, mas
1572
+
subtipos não podem herdar estrutura, só comportamentos, e só é permitido
1573
+
criar subtipos de tipos abstratos. Além disso, os métodos de Julia são
1574
+
implementados com despacho múltiplo—uma forma mais avançada do mecanismo de
1575
+
despacho único que vimos na <<single_dispatch_sec>>.((("",
0 commit comments