Ir para conteúdo

POWERED BY:

Arquivado

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

guih_oliveira10

nota para minha classe

Recommended Posts

Um exemplo do __construct, em uma classe @PDO, preste atenção que eu extendi a propria PDO pra fazer minhas abstrações

 

<?php
class PDOConnection extends PDO {

private $host 		;
private $database 	;
private $user 		;
private $password 	;
private $persistent = false;

public function __construct($host = 'localhost', $database = 'banco', $user = 'root', $password = '') {

	$this->host 	= $host;		
	$this->database = $database;
	$this->user 	= $user;
	$this->password = $password;

	set_exception_handler(array(__CLASS__, 'exception_handler'));

	$options = array(PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION, PDO::ATTR_PERSISTENT => $this->persistent);

	parent::__construct('mysql:host='.$this->host.';dbname='.$this->database, $this->user, $this->password,  $options);

	restore_exception_handler();

}

   public static function getInstance() {
       static $instance = NULL;

       if($instance == NULL) {
    	$instance = new PDOConnection;
       }

       return $instance;
   }


public static function exception_handler($exception) {
	die('[ERRO] Excecao: '. $exception->getMessage());
}

}
?>

 

Para usar ela;

$pdo = PDOConnection::getInstance();

$stmt = $pdo->prepare('UPDATE client SET time = :time, typing = :typing WHERE client_id = :client_id LIMIT 1');
$stmt->bindValue('client_id', $client['client_id']);
$stmt->bindValue('time', $lifeTimeClient);
$stmt->bindValue('typing', $typing);
$stmt->execute();

Compartilhar este post


Link para o post
Compartilhar em outros sites

<?php
class PDOConnection extends PDO {

private $host 		;
private $database 	;
private $user 		;
private $password 	;
private $persistent = false;

 

Você não precisa dessas propriedades, André.

 

public function __construct($host = 'localhost', $database = 'banco', $user = 'root', $password = '') {

	$this->host 	= $host;		
	$this->database = $database;
	$this->user 	= $user;
	$this->password = $password;

	set_exception_handler(array(__CLASS__, 'exception_handler'));

	$options = array(PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION, PDO::ATTR_PERSISTENT => $this->persistent);

	parent::__construct('mysql:host='.$this->host.';dbname='.$this->database, $this->user, $this->password,  $options);

	restore_exception_handler();

}

 

Cuidado André, isso é uma violação do princípio da substituicão de Barbara Liskov. As classes derivadas devem ser substituíveis por suas classes base.

 

   public static function getInstance() {
       static $instance = NULL;

       if($instance == NULL) {
    	$instance = new PDOConnection;
       }

       return $instance;
   }

 

Singleton não é aplicável aqui.

 

public static function exception_handler($exception) {
	die('[ERRO] Excecao: '. $exception->getMessage());
}

 

Isso é uma violação do princípio da responsabilidade única, não é responsabilidade dessa classes tratar erros.

Compartilhar este post


Link para o post
Compartilhar em outros sites

mysql.class.php

<?php

class mysql{

//Definições de variáveis
private $conn;
public $sql;

public function mysql($host,$user,$senha,$db){

	if($this->conn == NULL){

		$this->conn = mysql_connect($host,$user,$senha);
		mysql_select_db($db,$this->conn);

	}

}

//Função para fechar a conexão MYSQL
public function close_conn(){

	if($this->conn != NULL){

		unset($this->sql);
		mysql_close($this->conn);

	}

}

//Função anti-injection SQL
public function anti_injection($sintese){

	$sintese = strip_tags($sintese);
	$sintese = trim($sintese);

	if(!get_magic_quotes_gpc()){

		$sintese = mysql_real_escape_string($sintese,$this->conn);

	}

	return $sintese;

}

//Função que executa uma query no MYSQL
public function query($s){

	return $this->sql = mysql_query($s,$this->conn);

}

}


$a = new mysql('127.0.0.1','root','','teste');

?>

 

Compartilhar este post


Link para o post
Compartilhar em outros sites

há!!!

 

Olha só que bonito, como menos é mais!

 

:clap:

 

mysql.class.php

public function mysql($host,$user,$senha,$db){

 

Algum motivo específico para usar esse formato de constructor?

 

	if($this->conn == NULL){

 

Pode remover esse IF dai, quando esse objeto for construído, $conn será, invariavelmente, NULL.

 

Só tem mais um problema ai, você está olhando para essa classe sozinha, isso certamente fará você violar o princípio da inversão de dependência no futuro. Programe para abstrações, nunca para implementações.

Compartilhar este post


Link para o post
Compartilhar em outros sites

Algum motivo específico para usar esse formato de constructor?

 

Lendo uma apostila hoje, vi que colocando uma função com o mesmo nome da classe ela é automaticamente chamada quando iniciada a classe. Achei interessante usar pois elimina boa parte já.

 

Só tem mais um problema ai, você está olhando para essa classe sozinha, isso certamente fará você violar o princípio da inversão de dependência no futuro. Programe para abstrações, nunca para implementações.

 

Não consegui entender muito bem essa parte kkkkk

 

Acho que já dei um grande passo biggrin.gif

Compartilhar este post


Link para o post
Compartilhar em outros sites

ela é automaticamente chamada quando iniciada a classe.

 

É exatamente essa a função do construtor. A diferença é que usar o mesmo nome da classe é o estilo antigo, enquanto usar __construct() é o novo estilo desde o PHP 5.

 

Não consegui entender muito bem essa parte

 

Orientação a objetos é programar o relacionamento entre os objetos, ou seja, você tem uma peça do quebra-cabeça mas, ela sozinha, não serve para nada.

 

Poste um client para essa classe, que te mostrarei a violação ao princípio da inversão de dependências.

Compartilhar este post


Link para o post
Compartilhar em outros sites

É exatamente essa a função do construtor. A diferença é que usar o mesmo nome da classe é o estilo antigo, enquanto usar __construct() é o novo estilo desde o PHP 5.

 

Humm, mais uma coisa que aprendi, mais há algum problema em utilizar o método que utilizei ou e melhor usar o __construct()

 

Poste um client para essa classe, que te mostrarei a violação ao princípio da inversão de dependências.

 

client por acaso seria um exemplo da classe em funcionamento?

 

 

 

Compartilhar este post


Link para o post
Compartilhar em outros sites

há algum problema em utilizar o método que utilizei ou e melhor usar o __construct()

 

Nenhum problema, mas a linguagem evolui e é sempre bom acompanhar essas evoluções.

 

client por acaso seria um exemplo da classe em funcionamento?

 

client é um outro participante que USA sua classe.

Compartilhar este post


Link para o post
Compartilhar em outros sites

seria isso?

 

hummm, não.

 

Pense no quebra-cabeça, pense que sua classe mysql é apenas uma peça e que você precisa de várias peças para montar seu quebra-cabeça.

 

Clients são aquelas peças que se relacionam com sua peça mysql.

 

;)

Compartilhar este post


Link para o post
Compartilhar em outros sites
Cuidado André, isso é uma violação do princípio da substituicão de Barbara Liskov. As classes derivadas devem ser substituíveis por suas classes base.

 

JBN, não seria o contrário?

Pelo que aprendi, de acordo com o Pricípio de Substituição de Liskov diz que objetos da classes base podem ser substituída por objetos da classe derivada. :ermm:

 

Enfim, muitas pessoas não se dão conta do quão complexo é o assunto Orientação a Objetos. Não é só sair distribuindo classes por aí.

Eu mesmo, com 5 anos estudando e utilizando esse paradigma, ainda faço umas cagadas imensas.

Compartilhar este post


Link para o post
Compartilhar em outros sites

O Rick tem razão, para ser sincero nem sabia desse Princípio de Substituição de Liskov. :pinch:

O princípio foi definido de forma resumida como:

 

Se q(x) é uma propriedade demonstrável dos objetos x de tipo T. Então q(y) deve ser verdadeiro para objetos y de tipo S onde S é um subtipo de T.

 

Portanto, a visão de "subtipo" defendida por Liskov e Wing é baseada na noção da substituição; isto é, se S é um subtipo de T, então os objetos do tipo T, em um programa, podem ser substituídos pelos objetos de tipo S sem que seja necessário alterar as propriedades deste programa.

 

Então, o principio diz basicamente que:

 

class BaseClass {

}

class ExtendedClass extends BaseClass {

}

class TestClass {
   public function __construct( BaseClass $class )
   {
       //executa algum código com $class
   }
}

$testClass = new TestClass(new BaseClass);

//e

$anotherTestClass = new TestClass(new ExtendedClass);

 

Devem funcionar igualmente. É isso? Mas se for, isso não é basicamente o conceito de herança?

Compartilhar este post


Link para o post
Compartilhar em outros sites

Não, não tem nada a ver com isso.

O que é herança? Herança é um relacionamento do tipo 'é um'.

Um exemplo besta:

Temos uma classe Carro. Dela eu derivo uma classe Ferrari, beleza?

Está correto pois Ferrari É UM Carro.

 

Agora eu consigo substituir um Carro por uma Ferrari?

A princípio sim, pois uma Ferrari tem a mesma função que um Carro qualquer, ou seja, se locomove [a uma velocidade bem maior :assobiando:, é claro, mas ainda assim, executa a mesma função]

Compartilhar este post


Link para o post
Compartilhar em outros sites

Mas se eu implementar na Ferrari um metódo Run de forma diferente do esperado pelo código do cliente, eu acabaria quebrando o contrato que a minha classe tem com o cliente, correto?

 

Ex:

class Car {
   public function run()
   {
        return 'running...';
   }
}

class Ferrari extends Car {
   public function run()
   {
       throw new Exception('Ferrari sem gasolina');
   }
}

$car = new Car;
$car->run(); //funciona.
$ferrari = new Ferrari;
$ferrari->run(); //não vai funcionar.

Compartilhar este post


Link para o post
Compartilhar em outros sites

Mas aí é que tá, não importa a implementação. O princípio da substituição é definido em termos de funcionalidade.

Outra coisa, no seu exemplo, qualquer carro pode ficar sem gasolina, não só uma Ferrari.

Compartilhar este post


Link para o post
Compartilhar em outros sites

qualquer carro pode ficar sem gasolina, não só uma Ferrari.

 

Yep, mas ali foi só um exemplo, poderia ser

throw new Exception("Metódo não implementado ainda");

 

Apenas foi o que eu li: http://www.objectmentor.com/resources/articles/lsp.pdf

Compartilhar este post


Link para o post
Compartilhar em outros sites

Rapaz, não li o artigo pois é meio extenso e eu tenho que começar uma lista de exercícios de Linguagens Formais e Autômatos aqui, mas pensa assim: em PHP você não é obrigado a especificar um tipo de retorno para a função.

O que não ocorre na maioria das linguagens, como C++, Java, etc...

 

Como você vai implementar não importa, o que importa é a interface, ou seja, os métodos públicos que a sua classe possui.

Não sei se o seu exemplo se encaixa no que o LSP descreve. Na verdade, eu não sou um profundo conhecedor desse princípio, apenas foi mencionado em alguma das minhas aulas na faculdade.

Compartilhar este post


Link para o post
Compartilhar em outros sites

@João Batista Neto : agora entendi o que é client, vou amanha bem cedo postar um exemplo para analisarmos, pois agora estou indo viajar e já está quase na hora.

 

@JCMais: gostei muito do exemplo da ferrari kkkkk

Compartilhar este post


Link para o post
Compartilhar em outros sites

Poxa!!!

 

E não é que o tópico ficou divertido!!!

 

JBN, não seria o contrário?

 

Erro de digitação, os posts #23, #25, #27, #29 e #31 foram respondidos usando um tablet. Não é muito fácil responder usando um tablet.

 

:D

 

Pelo que aprendi, de acordo com o Pricípio de Substituição de Liskov diz que objetos da classes base podem ser substituída por objetos da classe derivada.

 

A substituição deve ser completa em termos comportamentais.

 

Se q(x) é uma propriedade demonstrável dos objetos x de tipo T. Então q(y) deve ser verdadeiro para objetos y de tipo S onde S é um subtipo de T.

 

Okay, você pegou uma definição formal na Wikipedia, mas o que isso significa?

 

O que torna uma classe substituível é o comportamento dela. Mas não o comportamento que programamos na classe derivada e sim o comportamento que confiamos e esperamos que a classe derivada deva ter segundo as regras definidas pela classe base.

 

Quando um client usa um objeto do tipo B, ele usa as operações definidas pela interface do tipo B, sabe quais são suas entradas e saídas. Mas o mais importante é que esse client conhece apenas o comportamento do tipo B.

 

Se derivarmos o tipo B criando um subtipo D e especializarmos a operação o(x), essa especialização deve ser totalmente compatível com a operação original do tipo B em termos de comportamento. Dizer que a classe derivada D deve substituir completamente a classe base B significa que os clients que usam o tipo B conhecem apenas o tipo B, se nosso tipo D se comportar diferente do esperado, então teremos que mudar os clients que usam o tipo B.

 

No caso do exemplo do carro:

 

<?php
class Car {
public function run() {}
}

 

O carro é a classe base, nossos clients sabem que se derem partida, e tiver combustível, eles poderão usar o carro para ir de um lugar à outro. O que faria uma classe derivada não substituir Car?

 

Qualquer coisa que não seja compatível com o comportamento esperado de um carro:

 

<?php
class OtherCar extends Car {
public function fly() {}

public function run() {
	$this->fly();
}
}

 

Se os clients que usam Car receberem OtherCar, vão esperar que o comportamento desse OtherCar seja compatível com Car, afinal, esses clients conhecem apenas o comportamento de Car e acreditam que receberam esse tipo. Mas vejam, OtherCar voa quando chamamos a operação run().

 

Esse é o comportamento esperado?

 

De fato, Car não é substituível por OtherCar pelo simples fato de OtherCar voar enquanto Car não voa.

 

É tudo uma questão de comportamento.

 

Um exemplo clássico é do retângulo e do quadrado. Do ponto de vista matemático, um retângulo possui 4 ângulos de 90 graus, possui 2 lados paralelos verticalmente e 2 lados paralelos horizontalmente:

 

<?php
class Rectangle {
private $height;
private $width;

public function getHeight() {
	return $this->height;
}

public function getWidth() {
	return $this->width;
}

public function setHeight( $h ) {
	$this->height = $h;
}

public function setWidth( $w ) {
	$this->width = $w;
}
}

 

$r = new Rectangle();
$r->setHeight( 10 );
$r->setWidth( 5 );

$a = $r->getHeight() * $r->getWidth();

printf( "A área do retângulo é %d\n" , $a );

 

A área do retângulo é 50

 

Ai lembramos também que, matematicamente falando, um quadrado é, por definição, um retângulo que possui os quatro lados iguais.

 

Ai pensamos: "Podemos usar herança!!!":

 

<?php
class Square extends Rectangle {
public function setHeight( $h ) {
	Rectangle::setHeight( $h );
	Rectangle::setWidth( $h );
}

public function setWidth( $w ) {
	Rectangle::setWidth( $w );
	Rectangle::setHeight( $w );
}
}

 

$r = new Square();
$r->setWidth( 5 );

$a = $r->getHeight() * $r->getWidth();

printf( "A área do quadrado é %d\n" , $a );

 

A área do quadrado é 25

 

Como o comportamento está de acordo com os fundamentos matemáticos, fazemos commit e ficamos felizes, mas.....

 

A grande preocupação do princípio da substituição de Liskov é que não é possível validar um modelo isoladamente. Em programação orientada a objetos, programamos o comportamento das coisas e como as coisas se relacionam.

 

O objeto Square pode até ser válido, quando observado isoladamente, mas quando colocado dentro de um contexto, ele passa a ser inválido:

 

<?php
class RectangleTest {
public function testArea( Rectangle $r ) {
	$r->setHeight( 10 );
	$r->setWidth( 5 );

	echo get_class( $r ) , ' => ';

	if ( $r->getHeight() * $r->getWidth() == 50 ) {
		echo 'pass';
	} else {
		echo 'fail';
	}

	echo PHP_EOL;
}
}

$t = new RectangleTest();
$t->testArea( new Rectangle() );
$t->testArea( new Square() );

 

Rectangle => pass

Square => fail

 

Como podemos ver, Square não é compatível com sua classe base, mesmo válido matematicamente, a classe Square comporta-se diferente da classe base e, por isso, não é uma substituição para Rectangle.

 

O grande ponto do exemplo do Rectangle e Square é demonstrar que, apesar de válido dizer que um quadrado é um retângulo matematicamente, em orientação a objetos, um objeto Square não é um objeto Rectangle.

 

E é muito simples visualizar o motivo de não sê-lo, para um objeto Square obedecer os fundamentos matemáticos, ele precisa que seus quatro lados sejam iguais. Porém, quando fazemos isso, adicionamos regras que fazem com que um objeto Square comporte-se diferente de um objeto Rectangle, ou seja, fazemos com que os clients que esperavam um determinado comportamento do objeto Rectangle, precisem ser modificados para receberem um objeto Square.

 

Na prática, apesar de válido matematicamente, um objeto Square não é um objeto Rectangle. Essa foi a motivação de Barbara Liskov ao estabelecer seu princípio da substituição.

 

EDIT:

 

Momento Jabá :seta: Curso PHP Orientado a Objetos

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.