Ir para conteúdo

Arquivado

Este tópico foi arquivado e está fechado para novas respostas.

rblazza

Objeto Orientado PHP

Recommended Posts

E aí, pessoal. Tudo bem com vocês? Bom, estou sendo muitas vezes perguntado sobre objetos orientados... E mesmo depois de ler alguns artigos, scripts, textos, livros... Ainda não entendi completamente. Acredito que um grande número de pessoas também passe por isso e tenha essa dúvida.

 

Quero saber das pessoas que sabem o que é e como funciona se, por favor, poderiam nos enviar sites, artigos ou dicas de como compreender esse tipo de código e como usá-lo no cotidiano durante o desenvolvimento. Como de costume, procurei aqui no fórum sobre isso e não achei nada que tirasse essa minha dúvida.

 

Enfim, desde já agradeço a atenção de todos! E claro, qualquer ajuda é bem vinda.

 

Obrigado! :-)

Compartilhar este post


Link para o post
Compartilhar em outros sites

Sei que para muitos isso vai parecer bobo, mas como disse, não sou expert em programação e muito menos em objeto orientado, estou estudando ambos. Eu bolei um exemplo só pra você me corrigirem e me dizerem o que estou fazendo de errado. Vamos ao exemplo:

 

Primeiro de tudo, crio as classes. Nesse caso, vou criar uma super classe onde vai ter uma sub-classe dentro, pra fazer o lance da herança também.

 

  • Arquivo: elfos.class.php
<?php

class Elfos {
public $nome;
public $reino;
public $idade;

function __construct($nome,$reino,$idade) {
$this->nome = $nome;
$this->reino = $reino;
$this->idade = $idade;

}

public function introducao() {
echo "O elfo $this->nome é pertencente ao reino $this->reino e tem $this->idade anos.";

}

}

?>
  • Arquivo: drow.class.php
<?php

class Drow extends Elfos {
public $classe;
public $caracteristica;

function __construct($nome,$reino,$idade,$classe,$caracteristica) {
parent::__construct($nome,$reino,$idade);
$this->classe = $classe;
$this->caracteristica = $caracteristica

}

function apresentacaoDrow() {
echo "Meu nome é $this->nome, tenho $this->idade e sou um $this->classe do reino $this->reino. Nós somos conhecidos por sermos $this->caracteristica. Por isso, somos temidos por todos!";

}

}

?>
  • Arquivo: index.php
<?php

include("elfos.class.php");
include("drow.class.php");

$elfo = new Drow("Ghaunandaur","Vhaerun",600,"Drow","negros como a escuridão e mortais como uma flecha envenenada");
$elfo->apresentacaoDrow();

?>

Enfim, fiz um exemplo curto. Mas gostaria de saber se estou pensando direito, quais meus erros e como poderia fazer melhor. :-)

 

Obrigado desde já.

Compartilhar este post


Link para o post
Compartilhar em outros sites

Estou meio sem tempo para um exemplo completo e para revisar tudo.

 

Vamos começar do básico da orientação, que é o reaproveitamento de código. Também é sempre important definir a visibilidade dos atributos e métodos.

 

Alterei a visibilidade de alguns atributos e removi o construtor. Primeiramente, pois a especialização define o atributo classe (Drow, MoonElf e sua característica (são elementos implícitos, e não explícitos como você fez).

 

Também não utilize echo dentro da sua classe, a classe define o comportamento do objeto e não da exibição/output.

 

 

Usarei seu mesmo exemplo e criarei a minha classe MoonElf.

<?php
class MoonElf extends Elfos {
    private $caracteristica = 'Impulsivo, extrovertido, frágil, tolerante';

    public function apresentacaoMoon() {
        $classe = get_class();
        
        return "Meu nome é $this->nome, tenho $this->idade e sou um $classe do reino $this->reino. 
        Nós somos conhecidos por sermos $this->caracteristica e somos temidos por todos!";
    }
}

Agora existe um problema, existe muito código repetido, por isso otimizarei na abstração:

class Elfos {
    /** códigos omitidos **/

    public function apresentacao() {
        return "Meu nome é $this->nome, tenho $this->idade e sou do reino $this->reino.
        Meu nome é $this->nome, tenho $this->idade";
    }
}

E a minha classe MoonElf é alterada para:

class MoonElf extends Elfos {
    
    /** códigos omitidos **/

    function apresentacao() {
        $classe = get_class();
        
        return parent::apresentacao()."
        Sou um $classe. Nós somos conhecidos por sermos $this->caracteristica e somos temidos por todos!";
    }
}

Assim que der, posto mais.

Compartilhar este post


Link para o post
Compartilhar em outros sites

Certo! Minhas dúvidas:

 

1) Então pelo que eu entendi, como a função do "elfos.class.php" não foi usada, você alterou pra uma que seja em comum para todas, no caso "apresentação", correto?

 

2) E a questão das características, você colocou como "private" pois não é pra ser usado como explícito. Mas isso é uma regra ou é algo que achou melhor pra esse exemplo?

 

3) Esse "get_class();" retira o valor dado pra classe em questão? No caso se fosse dado o nome de "Dwarfs", quando usado "$classe = get_class();" o nome retornado seria "Dwarfs", isso?

 

Obrigado!

Compartilhar este post


Link para o post
Compartilhar em outros sites

Observando as suas anotações e com outras coisas que vi até agora, cheguei nisso:

 

  • Classe Elfos:
<?php


abstract class Elfos {
public $nome;
public $reino;
public $idade;


function apresentacao();


}


?>
  • Classe Drow
<?php


final class Drow extends Elfos {
public $classe;
private $caracteristica;


function apresentacao() {


$classe = get_class();


return parent::apresentacao()." Sou um Sou um $classe. Nós somos conhecidos por sermos $this->caracteristica e somos temidos por todos!";


}


}


?>
  • Index:
<?php


include("elfos.class.php");
include("drow.class.php");


$elfo = new Drow("Ghaunandaur","Vhaerun",600,"Drow","negros como a escuridão e mortais como uma flecha envenenada");


$elfo->apresentacao();


?>

Tem alguma coisa errada? Obrigado! :-)

Compartilhar este post


Link para o post
Compartilhar em outros sites

Não entendi uma coisa.

você removeu o construct como você esta passando esses parâmetros?

 

 

Certo! Minhas dúvidas:

 

1) Então pelo que eu entendi, como a função do "elfos.class.php" não foi usada, você alterou pra uma que seja em comum para todas, no caso "apresentação", correto?

 

2) E a questão das características, você colocou como "private" pois não é pra ser usado como explícito. Mas isso é uma regra ou é algo que achou melhor pra esse exemplo?

 

3) Esse "get_class();" retira o valor dado pra classe em questão? No caso se fosse dado o nome de "Dwarfs", quando usado "$classe = get_class();" o nome retornado seria "Dwarfs", isso?

 

Obrigado!

1 - Elfo é usado apenas para apresentação, assim você esta dizendo todo e qualquer elfo se apresenta independente do que seja.

 

2- public, private, protected é chamado de visibilidade e é MUITO importante.

Quando você define um atributo / método como public você esta dizendo que tanto fora ou dentro do escopo você consegue acessar, isso quer dizer que se alguém tiver programando com você e for usar a sua classe ela pode acessar aquele atributo ou método quando criar a instancia.

class foo
{
public $attr = 'teste';

public function getAttr(){
return $this->attr();
}

$object = new foo();
echo $object->attr;
echo $object->getAttr();

Nesse caso a pessoa que instanciar seu objeto tem total acesso a sua propriedade e objeto, coisa que mudaria de figura se passar a colocar private.

 

Com private você só tem acesso ao atributo / método no escopo da sua classe ou seja dentro dela ou de suas extensões.

 

no seu exemplo se idade no objeto Elfo fosse private o drow ainda acessaria.

 

 

e o protected quer dizer que ninguém mais acessa a não ser ele mesmo, nem se quer subclasses podem ter acesso aquela informação.

 

Muito comum as pessoas usarem getter e setter não deixando os atributos públicos.

 

3 - Sim.

Compartilhar este post


Link para o post
Compartilhar em outros sites

Não entendi uma coisa.

 

você removeu o construct como você esta passando esses parâmetros?

Removi o construtor da classe especializada (Drow, MoonElf) e omiti o construtor da classe generalizada, pois estava sem tempo de colocar um exemplo completo.

Compartilhar este post


Link para o post
Compartilhar em outros sites
<?php
class MoonElf extends Elfos {
    private $caracteristica = 'Impulsivo, extrovertido, frágil, tolerante';

    public function apresentacaoMoon() {
}

E a minha classe MoonElf é alterada para:

class MoonElf extends Elfos {
    
    /** códigos omitidos **/

    function apresentacao() {
        $classe = get_class();
        
        return parent::apresentacao()

 

Sinto Gabriel, perdão de coração na minha forma de falar, mas isso aí não é orientação a objetos, você está apenas programando com "classes", como você falou que reescreveu, então agora é sua classe e não mais a do rapaz que está começando.

 

Sua reescrita não segue um padrão de design, viola a PSR-2 e outros princípios completamente.

// Pra que isso?
$classe = get_class();
// Usando PAAMAYIM NEKUDOTAYIM quando não é um método estático?
return parent::apresentacao()

Compartilhar este post


Link para o post
Compartilhar em outros sites

Em primeiro lugar, é sempre bom abrir discussões. Entretanto, o início básico da Orientação a objetos é "programar com classes", ou seja, entender o que realmente são classes e objetos, saber sobre construtor, métodos, atributos, herança. Após aprender toda a verticalidade da programação, vamos a parte horizontal (associação, agregação, composição). O que não foge em nada os links fornecidos pelo William Bruno, que alias, eu mesmo já li N vezes no passado.

 

Se você saiu de cara programando, em orientação à objetos, seguindo todos os design principles, não tenho nada mais a fazer do que te parabenizar.

Agora, se não, o exemplo ainda é válido para um iniciante.

Sua reescrita não segue um padrão de design, viola a PSR-2 e outros princípios completamente.

Saber e entender, não quer dizer seguir ela por completo. Em primeiro lugar todas as PSRs são apenas convenções, e não leis absolutas. As quais conheço e entendo, mas não concorco com todas. Acima de tudo, principalmente acima das PSRs, o padrão deve ser definido dentro da sua (no caso a minha) equipe de desenvolvimento. O qual já foi definido e não segue por completo a PSR (a maior base é do Robert C. Martin, com adições da PSR).

// Pra que isso?
$classe = get_class();

Ainda desenvolvo voltado para o PHP 5.4 e a ideia foi reduzir ao máximo o exemplo.

// Usando PAAMAYIM NEKUDOTAYIM quando não é um método estático?
return parent::apresentacao()

Saber o nome PAAMAYIM NEKUDOTAYIM é diferente de entender suas aplicações.
Só porque seu maior uso é com a keyword self, não quer dizer que é de uso exclusivo estático.

Parent é para chamar o objeto pai, pois se eu usasse $this, seria recursividade.
http://php.net/manual/en/keyword.parent.php

Compartilhar este post


Link para o post
Compartilhar em outros sites

Obrigado pelas respostas, pessoal.

 

Sobre a questão do private, public ou protected eu entendi. Eu fazia confusão antes, porque eu achava que se tratava de dados que não eram pra ser vistos pelo usuário. Mas aí consegui entender que é referente as classes, agora tudo bem. :-)

 

Agora sobre o resultado final, como ficaria? Confesso que fiquei um pouco perdido com a discussão de vocês, rs. As mudanças que eu fiz estão corretas no segundo exemplo? Tenho que manter construct? As variáveis $this?

 

Obrigado!

Compartilhar este post


Link para o post
Compartilhar em outros sites

×

Informação importante

Ao usar o fórum, você concorda com nossos Termos e condições.