DOO

diseño orientado a objetos

¿Porqué diseñar?

Mientras más temprana sea la etapa en donde se genere un defecto, más cuesta corregir el mismo

 

Conceptos para diseñar

  • Acoplamiento
  • Cohesión
  • Abstracción
  • Encapsulamiento
  • ....

Conceptos para diseñar I

Acoplamiento: grado de dependencia que tienen dos unidades de software

 

Cohesión: forma en la que agrupamos unidades de software en una unidad mayor

Conceptos para diseñar II

Abstracción: Aislar un elemento de su contexto o del resto de los elementos que lo acompañan.

 

Extensibilidad: Capacidad de un programa o clase por la cual permite extender funcionalidades con el menor impacto posible.

Conceptos para diseñar III

Law of Demeter
“Only talk to your immediate friends”


int price = customer.getOrder().getPrice();
int price = customer.getOrderPrice();

Conceptos para diseñar IV

Extensibilidad
Incorporar nuevo funcionamiento

Escalabilidad

Agregar capacidad

Conceptos para diseñar V

Herencia

Composición

Polimorfismo

Single Responsibility Principle
Open Close Principle
Liskov's Substitution Principle
Interface Segregation Principle
Dependency Inversion Principle

Single responsability principle

Una clase/método sólo debe tener una razón para cambiar (responsabilidad)

Single responsability principle

class Modem {

    void send(message) {
        // 1. dial-up
        // 2. send message
        // 3. hangup
    }
    string recv() {
        // receiving new message
        // 1. dial up
        // 2. receive message
        // 3. hangup
    }
}
class Modem {
    void send(message) {
        dial();
        // sending message
        hangup();
    }
    string recv() {
        dial();
        // receiving new message
        hangup();
    }  
    void hangup() {
        // do stuf...
    }  
    void dial(number) {
        // dialing number..
    } 
}

Open closed principle

Una clase debe permitir ser extendida (Open for Extensions), sin necesitar ser modificada (Close for modifications)

Open closed principle

class GraphicEditor {

    void DrawRectangle() {
        // ...
    }
    void DrawCircle() {
        // ...
    }
}

editor = new GraphicEditor();

if (type == 1)
    editor.DrawRectangle();
if (type == 2)
    editor.DrawCircle();
class GraphicEditor {

    void DrawFigure(Figure f)
        f.Draw();
    }
}

class Figure {
    void Draw();
}

class Rectangle extends Figure {
    void Draw() {
        // draw
    }
}

Liskov's Substitution Principle

Una clase derivada debe poder ser reemplazada en su totalidad por una clase base

Liskov's Substitution Principle

public interface IDuck {
    void Swim();
}
public class Duck : IDuck {
    public void Swim() {
        //do something to swim
    }
}
public class ElectricDuck : IDuck {
    public void Swim() {
        if (!IsTurnedOn)
           this.TurnOn();
        //swim logic  
    }
    public void TurnOn() {
        this.turnOn = True;
    }
}

void MakeDuckSwim(IDuck duck) {
        duck.Swim();
}
public interface IDuck {
    void Swim();
}
public class Duck : IDuck {
    public void Swim() {
        //do something to swim
    }
}
public class ElectricDuck : IDuck {
    public void Swim() {
        if (!IsTurnedOn)
           return;
    }
    public void TurnOn() {
        this.turnOn = True;
    }
}

void MakeDuckSwim(IDuck duck) {
    if (duck is ElectricDuck)
        ((ElectricDuck)duck).TurnOn();
    duck.Swim();
}

Interface Segregation Principle

No se debe forzar a una clase a depender de interfaces que no utiliza

Interface Segregation Principle

interface IWorker {
    public void work();
    public void eat();
}
class Worker implements IWorker{
    public void work() {
	// working
    }
    public void eat() {
	// eating in launch break
    }
}

class RobotWorker implements IWorker {
    public void work() {
        // working
    }
    public void eat() {
        // i dont have to eat
    }
}
interface IWorkerable {
    public void work();
}
interface IFeedable {
    public void eat();
}

class Worker implements IWorkerable, IFeedable {
    public void work() {
	// working
    }
    public void eat() {
	// eating in launch break
    }
}

class RobotWorker implements IWorker {
    public void work() {
        // working
    }
}

Las abstracciones no deben depender de los detalles, los detalles deben depender de las abstracciones.

Dependency Inversion Principle

Dependency Inversion Principle

class Worker {
    public void work() {
	// ....working
    }
}
class Manager {
    Worker worker;
    public void setWorker(Worker w) {
	worker = w;
    }
    public void manage() {
	worker.work();
    }
}
class SuperWorker {
    public void work() {
	//.... working much more
    }
}
interface IWorker {
    public void work();
}
class Worker implements IWorker {
    public void work() {
        // ....working 
    }
}
class SuperWorker implements IWorker {
    public void work() { 
        //.... working much more 
    }
}
class Manager {
    IWorker worker;
    public void setWorker(IWorker w) {
	worker = w;
    }
    public void manage() {
	worker.work();
    }
}

Ejercicio: CoffeMaker

Ver: Articulo relacionado (pag 123)

Patrones de diseño

<GoF>

  • Erich Gamma
  • John Vlissides
  • Ralph Johnson
  • Richard Helm

¿Qué son?

  • Catálogo reutilisable
  • Vocabulario común
  • Facilitar el aprendizaje
  • Estandarización

¿Qué NO son?

No pretenden ser recetas mágicas
ni eliminar la creatividad.

 

Para realizar un buen diseño basta con entender el modelo de negocio

Patrones/categorias

  • Creational Design Patterns
    • Singleton, Factory, ...
  • Behavioral Design Patterns
    • Observer, Strategy, Command, CoR, ...
  • Structural Design Patterns
    • Adapter, Composite, Decorator, ...

Singleton

"One instance to rule them all"

Factory

Observer

Strategy

Chain of Responsibility

Command

Iterator

Decorator

Composite

Proxy

Ejemplos

Gracias!

Diseño POO

By Gabriel Fusca

Diseño POO

  • 393