Modelo de orientação a objetos de PHP 3 e 4

A versão 3 de PHP já suportava a programação orientada a objetos (POO), embora seja verdade que a maioria das características deste tipo de programação ainda não estavam implementadas. Teoricamente, com PHP3 podíamos criar classes e instanciar objetos. As classes permitiam agrupar tanto métodos como propriedades ou atributos, mas a coisa ficava por aí.

Em PHP4, se reescreveu o motor de PHP para torná-lo muito mais rápido e estável, mas a POO, que havia introduzido a versão anterior da linguagem, praticamente não chegou a se modificar. Mesmo assim, durante a vigência de PHP 4, a programação orientada a objetos foi utilizada habitualmente, muitas vezes em aplicações de grande tamanho. Até que se manifestou a falta de potência da POO em PHP 4 e a necessidade de melhora-la em uma nova versão.

O maior problema da POO nas versões 3 e 4 de PHP se baseava em que, cada vez que se atribuía uma variável que continha um objeto a outra variável, ou se passava um objeto por parâmetro em uma função, se realizava uma cópia (um clone) desse objeto e ficava à disposição do programa na nova variável ou parâmetro.

$carol = new pessoa(“carol”);
$carol2 = $carol;

Em um código como o anterior, se tiver um objeto pessoa alojado na variável $carol e na segunda linha de código, cria-se um clone de $carol e se atribui à variável $carol2. Neste caso e sempre seguindo o anterior modo de trabalho de PHP, embora $carol e $carol2 contenham um objeto idêntico, não se trata do mesmo objeto e sim, de uma cópia. Tudo isto implica que o espaço de memória para salvar os dois objetos é o dobro que se fosse um mesmo objeto com dois nomes distintos.

Esta situação ocorreria porque os objetos eram tratados da mesma forma que as variáveis normais, que se passam por valor nas funções e no caso de se atribuir, se realiza uma cópia da variável antes de se atribuir ao novo espaço.

Exemplo da forma de trabalho com objetos de PHP 3 e 4

Vamos realizar um exemplo para ilustrar a forma de trabalho de PHP 3 e 4 com os objetos. Neste exemplo poderá ficar patente o processo de clonagem dos objetos ao serem passados em uma função ou ao se atribuírem a outra variável.

Primeiro, veremos uma declaração de um objeto muito simples. Trata-se de uma “caixa” que tem um atributo que é o conteúdo e dois métodos, um para introduzir novos conteúdos na caixa e outro para mostrar o conteúdo atual da caixa.

class Caixa{
var $conteudo;

function introduz($coisa){
$this->conteudo = $coisa;
}

function mostra_conteudo(){
echo $this->conteudo;
}
}

Agora veremos poucas linhas de código que fazem uso da classe Caixa para ilustrar a forma de trabalho dos objetos em PHP 4. Vamos instanciar o objeto, logo o atribuímos a outra variável, com o qual se criará um clone desse objeto, continuamos modificando o clone e veremos o que acontece.

$minhacaixa = new Caixa();
$minhacaixa->introduz(“algo”);
$minhacaixa->mostra_conteudo();

“<br>”;

$segunda_caixa = $minhacaixa;
$segunda_caixa->introduz(“conteudo na segunda caixa”);
$segunda_caixa->mostra_conteudo();

“<br>”;

$minhacaixa->mostra_conteudo();

Na primeira linha de código se instancia a caixa e se aloja o objeto na variável $minhacaixa. Na segunda linha se introduz o string “algo” no conteúdo da caixa. Logo, mostra-se o conteúdo, com o que sairá o string “algo” na página web.

No segundo bloco de código se atribui o objeto $minhacaixa à variável $segunda_caixa, com o que se cria o mencionado clone do objeto $minhacaixa e se atribui à nova variável. Logo, introduzimos um novo conteúdo à instancia alojada na variável $segunda_caixa. Atenção aqui, porque o clone alojado foi modificado na variável $segunda_caixa, deixando inalterável o objeto original $minhacaixa.

Para comprovar, mostra-se o conteúdo do objeto $segunda_caixa, com o que aparece na página web o string “conteúdo em segunda caixa”. Também se mostra o conteúdo $minhacaixa, que não se modificou apesar de atualizar o conteúdo de seu clone, com o que se mostra o string “algo”.

Espero que não seja muito difícil de entender. Vocês mesmos podem provar para compreender bem o exercício. De qualquer forma, vamos dar outro exemplo o qual se utiliza a classe Caixa, que esperamos que sirva para esclarecer melhor o trabalho com objetos em PHP 3 e 4.

$minhacaixa = new Caja();
$minhacaixa->introduz(“algo”);
$minhacaixa->mostra_conteudo();

“<br>”;

function vazia_caixa($caixa_esvaziar){
$caixa_esvaziar->introduz(“pó”);
}

vazia_caixa($minhacaixa);

$minhacaixa->mostra_conteudo();

Neste exemplo, criamos uma função que recebe por parâmetro um objeto da classe caixa. Como os parâmetros nas funções são recebidos por valor ao invés de referência, quando se passa o parâmetro do objeto caixa, no fundo o que se está realizando é uma cópia desse objeto, de modo que dentro da função se trabalha com um clone do objeto, ao invés do objeto mesmo.

No código se instancia o objeto caixa e se introduz “algo” em seu conteúdo. Logo, se declara uma função que recebe o objeto e modifica seu conteúdo, introduzindo o string “pó” no conteúdo da caixa. Nas seguintes linhas de código, chama-se a função declarada anteriormente, passando por parâmetro o objeto $minhacaixa. Dentro da função, como dizia, modifica-se o conteúdo da caixa, embora realmente se esteja modificando o conteúdo de um clone.

Por último, mostra-se o conteúdo do objeto $minhacaixa. Neste caso aparece “algo”, apesar de que na função esse “algo” se modificou por “pó”. Apesar de poder parecer chato, volto a repetir que na função se modificou um clone do objeto e não o objeto original.

Os comportamentos descritos anteriormente não são muito habituais em outras linguagens de programação orientada a objetos, como Java, onde o objeto não se duplica cada vez que se realiza uma atribuição ou um passo por parâmetro.

Para evitar o comportamento que descrevemos, PHP dispõe da opção de passo de parâmetros por referência, que se realiza com o caractere “&”. Por exemplo, para atribuir o próprio objeto e não um clone, poderíamos ter utilizado este código:

$segunda_caixa = &$minhacaixa;

Para receber um parâmetro por referência ao invés de por valor em uma função utilizaríamos esta declaração de função:

function vazia_caixa(&$caixa_esvaziar){

A possibilidade de utilizar o caractere “&” para forçar um passo por referência não deixa de ser um problema, visto que nos obriga a utilizar esse mecanismo em múltiplos lugares e é muito fácil se esquecer do “&” em algum lugar, com o qual nosso programa já não realizará os resultados esperados. Muitos programadores gastaram horas para encontrar o problema e de qualquer forma, é um incômodo ter que estar pendentes de incluir constantemente o signo “&” no código para fazer com que funcione como eles desejam.

Fonte: http://www.criarweb.com/artigos/328.php

Deixe um comentário