Coletânea Python do ZERO às Redes Neurais Artificiais
Variáveis vs Objetos
Partindo para a prática, vamos inicialmente entender no código quais
seriam as diferenças em um modelo estruturado e em um modelo orientado a objetos.
Para esse exemplo, vamos começar do básico apenas abstraindo uma situação onde simplesmente teríamos de criar uma variável de nome pessoa1 que recebe como atributos um nome e uma idade.
Inicialmente raciocine que estamos atribuindo mais de um dado (nome e
idade) que inclusive serão de tipos diferentes (para nome uma string e para idade um int).
Convencionalmente isto pode ser feito sem problemas por meio de um dicionário, estrutura de dados em Python que permite o armazenamento de dados em forma de chave / valor, aceitando como dado qualquer tipo de dado alfanumérico desde que respeitada sua sintaxe:
Então, finalmente dando início aos nossos códigos, inicialmente criamos na primeira linha uma variável de nome pessoa1 que por sua vez, respeitando a sintaxe, recebe um dicionário onde as chaves e valores do mesmo são respectivamente Nome : Fernando e Idade : 32.
Em seguida usamos a função print( ) para exibir o conteúdo de pessoa1.
O retorno será: Nome : Fernando, Idade : 32
Como dito anteriormente, nesses moldes, temos uma estrutura estática, onde podemos alterar/adicionar/remover dados manipulando o dicionário, mas nada além das funcionalidades padrão de um dicionário.
Partindo para um modelo orientado a objetos, podemos criar uma classe
de nome Pessoa onde Nome e Idade podem simplesmente ser variáveis com seus respectivos atributos guardados lá dentro. E não nos limitamos somente a isso, podendo adicionar manualmente mais características a pessoa1 conforme nossa necessidade.
Inicialmente, pela sintaxe Python, para criarmos a estrutura de uma classe de forma que o interpretador faça a sua leitura léxica correta, precisamos escrever class seguido do nome da classe, com letra maiúscula apenas para diferenciar do resto.
Dentro da classe, aqui nesse exemplo, colocamos apenas o comando pass, dessa forma, esta será inicialmente uma classe “em branco”, por enquanto vazia.
Na sequência, fora da classe (repare pela indentação) criamos o objeto de nome pessoa1 que inicializa a classe Pessoa sem parâmetros mesmo, apenas a colocando como atributo próprio.
Em seguida, por meio do comando pessoa1.Nome, estamos criando a variável Nome dentro da classe Pessoa, que por sua vez recebe ‘Fernando’ como atributo, o mesmo é feito adicionando a variável Idade com seu respectivo valor.
Note que em comparação ao código anterior temos mais linhas de código e de maior complexidade em sua lógica sintática, neste exemplo em particular ocorre isto mesmo, porém você verá posteriormente que programar blocos de código dentro de classes assim como as modularizar tornará as coisas muito mais eficientes, além de reduzir a quantidade de linhas/blocos de código.
Tratando os dados como instâncias de uma classe, temos liberdade para adicionar o que quisermos dentro da mesma, independente do tipo de dado e de sua função no contexto do código.
Repare que seguindo com o exemplo, adicionalmente inserimos um dicionário de nome Documentos com valores de Identidade e CPF, assim como uma lista de nome Pais que tem atribuída a si Alberto Feltrin e Tânia Feltrin.
Toda essa estrutura, guardada na classe Pessoa, se fosse ser feita de forma convencional estruturada demandaria a criação de cada variável em meio ao corpo do código geral, dependendo o contexto, poluindo bastante o mesmo e acarretando desempenho inferior em função da leitura léxica do interpretador da IDE.
Sendo assim, aqui inicialmente apenas mostrando de forma visual os primeiros conceitos, podemos começar a entender como se programa de forma orientada a objetos, paradigma este que você notará que será muito útil para determinados tipos de códigos / determinados tipos de problemas computacionais.
Nos capítulos subsequentes, gradualmente vamos começar a entender as funcionalidades que podem ser atribuídas a uma classe de um determinado objeto, assim como a forma como instanciaremos dados internos desse objeto para interação com outras partes do código geral.
Outro ponto a levar em consideração neste momento inicial, pode estar parecendo um pouco confuso de entender a real distinção entre se trabalhar com uma variável (programação estruturada) e um objeto (programação orientada a objetos).
Para que isso fique bem claro, relembre do básico da programação em Python, uma variável é um espaço de memória alocado onde guardamos algum dado ou valor, de forma estática.
Já na programação orientada a objetos, uma variável ganha “super poderes” a partir do momento em que ela possui atribuída a si uma classe, dessa forma ela pode inserir e utilizar qualquer tipo de dado que esteja situado dentro da classe, de forma dinâmica.
Supondo que pela modularização tenhamos um arquivo de nome pessoa.py, dentro de si o seguinte bloco de código, referente a uma classe vazia.
Agora, em nosso arquivo principal de nome main.py realizamos a importação dessa classe Pessoa e a atribuímos a diferentes variáveis/objetos.
Diferentemente da programação estruturada, cada variável pode usar a classe Pessoa inserindo diferentes dados/valores/atributos a mesma.
Neste contexto, a classe Pessoa serve como “molde” para criação de outros objetos, sendo assim, neste exemplo, cada variável que inicializa Pessoa( ) está criando toda uma estrutura de dados única para si, usando tudo o que existe dentro dessa classe (neste caso não há nada mesmo, porém poderia ter perfeitamente blocos e mais blocos de códigos...) sem modificar a estrutura de dados da classe Pessoa.
Por meio da função print( ) podemos notar que cada variável pessoa está alocada em um espaço de memória diferente, podendo assim usar apenas uma estrutura de código (a classe Pessoa) para atribuir dados/valores a cada variável (ou para mais de uma variável).
Raciocine inicialmente que, a vantagem de se trabalhar com classes, enquanto as mesmas tem função inicial de servir de “molde” para criação de objetos, é a maneira como podemos criar estruturas de código reutilizáveis.
Para o exemplo anterior, imagine uma grande estrutura de código onde uma pessoa ou um item teria uma série de características (muitas mesmo), ao invés de criar cada característica manualmente para cada variável, é mais interessante se criar um molde com todas estas características e aplicar para cada nova variável/objeto que necessite destes dados.
Em outras palavras, vamos supor que estamos a criar um pequeno banco de dados onde cada pessoa cadastrada tem como atributos um nome, uma idade, uma nacionalidade, um telefone, um endereço, um nome de pai, um nome de mãe, uma estimativa de renda, etc...
Cada dado/valor destes teria de ser criado manualmente por meio de variáveis, e ser recriado para cada nova pessoa cadastrada neste banco de dados... além de tornar o corpo do código principal imenso.
É logicamente muito mais eficiente criar uma estrutura de código com todos estes parâmetros que simplesmente possa ser reutilizado a cada novo cadastro, ilimitadamente, simplesmente atribuindo o mesmo a uma variável/objeto, e isto pode ser feito perfeitamente por meio do uso de classes (estrutura de dados de classe / estrutura de dados orientada a objeto).
Entendidas as diferenças básicas internas entre programação estruturada
convencional e programação orientada a objetos, hora de começarmos a de fato criar nossas primeiras classes e suas respectivas usabilidades, uma vez que como dito anteriormente, este tipo de estrutura de dados irá incorporar em si uma série de dados/valores/variáveis/objetos/funções/etc... de forma a serem usados, reutilizados, instanciados e ter interações com diferentes estruturas de blocos de código.