MartinDardis / Algoritmos-3-FIUBA

Repositorio del Trabajo practico 2 de algoritmos y programacion 3 - AlgoEmpire
http://codeahastalamuerte.com/
2 stars 0 forks source link

Dudas TP 2 #2

Open maguimarijuan opened 6 years ago

maguimarijuan commented 6 years ago

Abro este issue para que me consulten sus dudas de la primera entrega! Abriremos distintos issues para los problemas que tengan. Saludos!

lorenzolgz commented 6 years ago

¡Buen día!

Pensando en la re-implementación del patrón de estados de reparacion para los edificios se me presentó un problema.

Lo que quiero lograr es que como hablamos el comportamiento de reparar() esté contenido dentro de cada estado (daniado, yaReparado, vidaCompleta, etc) pero si lo que reparar debe hacer es cambiar el valor del atributo vida del edificio, ¿cómo podemos implementar eso?

Ordeno un poquito la pregunta, ¿Cómo podríamos desde estadoReparacion modificar un atributo (vida) que es de la clase Edificios?

Saludos, Lorenzo

maguimarijuan commented 6 years ago

Buenas! mmm qué buena pregunta! ja! ¿Tendría sentido que la vida sea un atributo del estado? Capaz por acá hay una posible solución. Que cada estado pueda responder a la cantidad de vida. Creo que hay un estado que es vida completa una vez que sale de este estado pasa a otro que es estado a reparar y administra la vida de manera distinta. No se si es una buena solución (no hay soluciones buenas) pero capaz va por ahí. De otra manera, podemos seguir charlandolo.

Saludos!

lorenzolgz commented 6 years ago

¡Capaz que si! Mañana voy a intentar implementarlo, gracias por la pronta respuesta

Saludos!

lorenzolgz commented 5 years ago

Hola Magui!

Recién pushee una refactorización de los estados en algo más orientado a lo que habíamos hablado (que reparar() sea un metodo propio del estado) pero aún hay una pequeña parte de la implementación que si o si debe estar "expuesta" en edificio, que es cuando yo tengo que hacer transicionar un estado a otro (por ejemplo de daniado a vidaCompleta o de daniado a YaReparado) y eso está en el método actualizarEstado() propio de edificio que se llama luego de reparar()

No se me ocurrió algo mas "limpio", despues si le podes echar un ojo te lo re agradecería

Saludos y buen finde!

MartinDardis commented 5 years ago

Hola Magui!

Seria algo logico mostrarle al usuario (ya sea mediante un menu o lo que sea) ataques que solo son posibles con la unidad con la que esta? Re armando un poco, solo mostrarle los ataques q puede hacer si quiere atacar y no dejar que envie un ataque a una posicion no valida ( ya sea porque esta vacia o porque esta fuera de su rango )?

maguimarijuan commented 5 years ago

Hola Magui!

Recién pushee una refactorización de los estados en algo más orientado a lo que habíamos hablado (que reparar() sea un metodo propio del estado) pero aún hay una pequeña parte de la implementación que si o si debe estar "expuesta" en edificio, que es cuando yo tengo que hacer transicionar un estado a otro (por ejemplo de daniado a vidaCompleta o de daniado a YaReparado) y eso está en el método actualizarEstado() propio de edificio que se llama luego de reparar()

No se me ocurrió algo mas "limpio", despues si le podes echar un ojo te lo re agradecería

Saludos y buen finde!

Ahora veo esto y les doy una mano!

maguimarijuan commented 5 years ago

Hola Magui!

Seria algo logico mostrarle al usuario (ya sea mediante un menu o lo que sea) ataques que solo son posibles con la unidad con la que esta? Re armando un poco, solo mostrarle los ataques q puede hacer si quiere atacar y no dejar que envie un ataque a una posicion no valida ( ya sea porque esta vacia o porque esta fuera de su rango )?

Mmmm! Creo que tenes dos opciones: -Mostrale todos los ataque posibles y avisarle con un cartel cuando haga click en alguno no posible. -Mostrale sólo los que puede hacer.

Si entiendo bien tu pregunta las dos opciones están bien siempre que no se de el caso que se produzca algún movimiento inválido.

Saludos! perdón la tardanza.

MartinDardis commented 5 years ago

Hola magui, te dejo un diagrama tentativo del modelo que estamos pensando, te lo resumo un poco

hay 1 clase jugador que contiene

Cada Jugador tiene:

Cada Elemento tiene

Asi tambien el casillero tiene una referencia al elemento al que contiene pudiendo acceder a el mediante un casillero, o acceder a un casillero mediante un elemento

El mapa no hace distincion entre jugadores solo tiene una lista de casilleros.

Enlace

maguimarijuan commented 5 years ago

Hola! Estuve viendo su TP y tengo un par de observaciones: (les dije que no trabajaran en distintos branches, me costó ver todo asique si falta algo avisenme) 1) En cuanto a los commits personals creo que los tres están trabajando parejo. 2) En cuanto a las pruebas, faltan un par y algunas tienen dos asserts, asegurense de que sean incrementales y unitarias. 3) Yo se que les había dicho que tengan un "actualizar estado" pero ahora que lo veo es horrible jaja, Creo que reparar debería devolver una instancia del estado. 4) No hay cambios en coordenadas. Veo que trataron de implementar lo de la lista en mapa pero aún así no lo hicieron del todo. 5) Busquen algún patron "creacional" para el mapa como un factory quizas. 6) El método de actualizar jugador (en la clase partida) se les ocurre alguna menara de quitar ese if (por qué no se conocen los jugadores y ellos devuelve quién sigue, imaginen que en vez de Age of Empires fuera algún juego de cartas e implementaran así como hicieron la ronda, sería un horror) 7) Construir edificio sigue recibiendo las coordenadas. Se rompe el encapsulamiento. 8) ¿Quién settea el estado de aldeano? Aquel que lo haga sabe que aldeano tiene estados y se rompe el encapsulamiento. No sería mejor que le diga aldeano "construí" y aldeano modifique o no su estado. 9) Sean creativos y busquen otro patrón para el TP -> suma muchisimos puntos. 10) Para el jueves hagan diagramas de secuencias y de clases que vamos a ver muchisimo el modelo para que puedan hacer la interfaz. Si arreglan las cosas que mencioné antes empiecen con la interfaz.

Saludos!

maguimarijuan commented 5 years ago

Seguro que a la noche lo vuelvo a ver para ver más correcciones porque siempre hago dos o tres vistas al código.

lorenzolgz commented 5 years ago

Hola, Magui

¡Gracias por todo el feedback! Me gustaría replicar un par de detalles que estuvimos arreglando sobre las observaciones.

Sobre todas las otras observaciones estamos trabajando

De nuevo muchas gracias por tomarte el tiempo

Saludos!

lorenzolgz commented 5 years ago

Yo se que les había dicho que tengan un "actualizar estado" pero ahora que lo veo es horrible jaja, Creo que reparar debería devolver una instancia del estado.

¡Con esta me partiste al medio! En nuestra implementación cuando a un aldeano que no puede reparar se le pide unAldeano.reparar() , lanza AldeanoOcupadoError y si eso sucede (no estoy seguro, lo googlé nada mas jaja) no seguiría ejecutando el método y el return no se haría, por ende no se como sería.

Trato de ejemplificarlo mas facil:

Tenemos esto

//////En aldeano///////
public void reparar(unEdificio){
       this.estadoReparacion.reparar(unEdificio);
       this.estadoReparacion = this.estadoReparacion.actualizarEstado();
}

Si quisieramos algo así


//////En aldeano///////
public void reparar(unEdificio){
       this.estadoReparacion =  this.estadoReparacion.reparar(unEdificio); /// <-- acá que pasa?
}

donde la excepción se llamaría en:

//////En un estado donde NO se puede reparar (por ejemplo constructor)///////
public EstadoReparacion reparar(unEdificio){

       public EstadoReparacion reparar(unEdificio){
                    throw new AldeanoOcupadoError();   ////<---- acá se lanza
                    return new EstadoConstructor();
        }
}

Si desde el reparar de estado se lanza una excepción, ¿va a devolver ese nuevo estado estado? ¿o va a devolver null?

lorenzolgz commented 5 years ago

Ültima! (perdon por mandar todo junto es que después hasta la noche no vuelvo a codear)

De momento el Unidad.mover(unCasillero) solo verifica que el casillero este vacío, y que esté a una distancia menor a uno, pero el comportamiento que falta agregar es que solo se puedan mover una vez por turno, y quiero inclinarme por algún patron de diseño pero no se cual, y además tengo un pequeño dilema.

El mover está asi:

////En Unidad.java
    public void mover(Casillero nuevoCasillero)throws CasilleroAlejadoError, LugarOcupadoError {

        if(this.posicion.distanciaHasta(nuevoCasillero) > 1)
            throw new CasilleroAlejadoError();
        if(nuevoCasillero.estaOcupado())
            throw new LugarOcupadoError();

        this.posicion.remover();

        nuevoCasillero.colocar(this);   ///// Esto es lo que no se me ocurre hacer desde un estado
        this.posicion = nuevoCasillero;   //// Esto si se puede, si hacemos "posicion" un atributo de estado

    }

Dado que al mover yo tengo que decirle al nuevoCasillero "bueno, ahora yo <> estoy adentro tuyo" toda idea de tipo "bueno, hago que la posición no sea de cada unidad, sino de una clase Estado que la permita o no moverse (algo parecido a como la vida es de EstadoReparacion en edificios)" se me cayeron porque cómo le digo desde Estado al casillero que guarde a la Unidad que lo tiene como atributo.

Un re lío de palabras, yo había pensado algo así:

Unidad -(tenga)--> EstadoMovimiento --(tenga)--> PosicionActual y metodo mover(Casillero)

Pero como hago si le paso el comportamiento a un EstadoMovimiento para que guarde en casillero una referencia de la Unidad

maguimarijuan commented 5 years ago

Respecto al State! Tenés razón, el método set state o actualizar tiene que estar (https://www.youtube.com/watch?v=MGEx35FjBuo) ahí hay un video de como implementarlo correctamente. Tenía razón la primera vez que lo vi y no se porque la segunda dudé. Te pido disculpas. Eso es para el primer issue. Esa cuenta de youtube esta mucho muy buena asique si pueden mirenla.

maguimarijuan commented 5 years ago

Sobre la segunda preguntas, si un state sería una solución buena pero respondiendo la siguiente pregunta: "Pero como hago si le paso el comportamiento a un EstadoMovimiento para que guarde en casillero una referencia de la Unidad" se me ocurre que estadoMovimiento le diga a casillero: "puedo entrar" y se mande como paramétro (usando self). Me estaría costando una solución, lo estuve pensado y no se me ocurre otra cosa.

Perdonen, voy a consultar otra idea con mis compañeros.

Saludos!

maguimarijuan commented 5 years ago

Claro, pero ahora que lo pienso, state le tendría que decir a unidad que le diga a casillero que lo guarde... qué complicado!

Sigo pensandolo jaja!

maguimarijuan commented 5 years ago

Como el jueves no va a haber clases, la entrega será online por lo tanto les pido que el jueves (a más tardar el viernes porque tardé en responder y todavía me queda rondando en la cabeza la pregunta anterior) suban una carpeta a git con un par de diagramas de secuencia de estas situaciones y un par de diagramas de clase. Les sugiero que (para ya ir armando el informe) a cada diagrama le agreguen un pequeño texto de qué es lo que resuelven y qué problemas enfrentaron.

También es importante que ya tengan terminado el modelo para empezar con la interfaz gráfica (hagan lo que más puedan).

Saludos!

lorenzolgz commented 5 years ago

Hola Magui, viendo cómo estamos la verdad si nos permitís extendernos hasta el viernes para esta entrega vamos a poder llegar con algo bastante más armado. Voy a corregir el tema estado y respecto del mover() que quedó pendiente...

Se me ocurrió (aún no pude implementarlo) que el estadoMovimiento.mover() devuelva el casillero al que la unidad puede moverse de manera que:

-En un estado donde pueda moverse, devuelve el que le corresponde

-En uno dónde no, devuelve en el que la unidad ya estaba.

Se me hace un poco rudimentario pero estuve pensandolo y no se me ocurre una solución más linda

maguimarijuan commented 5 years ago

Oki! Hagan una opción que funcione y después lo optimizamos. Terminen el modelo!!! La entrega la paso para el viernes a la noche.

Saludos!

maguimarijuan commented 5 years ago

Hola! ¿Cómo están? Estuve viendo su tp! va muy bien! avisenme si tiene alguna duda! Esta noche subo más comentarios.

Estuve con los chicos y no pudimos correr las pruebas, no sé si es un problema mío o si ustedes usaron JUnit 5 y JUnit 4 o algo así raro. Por lo tanto, les pido que me manden qué versión usaron.

Estuve viendo todo lo que está en el branch nuevo modelo. Por lo tanto, si quieren usar distintos branchs haganlo por funcionalidad, pero les recomiendo que usen 1 sola y que unan todo!!!!

Vi los primeros pasos de la interfaz gráfica. Muy buena la presentación!!!

La entrega 3 está aprobada!

Saludos!

PD: Si alguno quiere saber la nota del recuperatorio me puede mandar una mail y les averiguo.

lorenzolgz commented 5 years ago

Hola Magui, ¡gracias! - Si, nos estamos manejando con nuevoModelo para el desarrollo y cada tanto hacemos un PR a Master.

Respecto de JUnit, si no estoy equivocado usamos JUnit 4.11 pero ahora que lo mencionas capaz que hay alguna prueba que justo necesitabamos un assert medio rancio e incluímos un paquete que no iba (ej: AssertNotSame)

Aprovecho para hacerte una pregunta del tema Interfaz, más que de interfaz, de MVC, ¿es necesario que tambien utilizemos patrones de diseño y seamos "polimorficos" para esta parte del trabajo? Por ejemplo, a la hora de dibujar un casillero de un color o de otro (según la unidad que tenga) lo que esta hecho es para un casillero que tiene una entidad Posicionable (interfaz de Unidades y Edificios)

if entidad instanceOf(Aldeano)   -----> dibuja el colorcito del aldeano y ponele una A al botón
if entidad instanceOf(Castillo)   -----> dibuja el colorcito del castillo y ponele una C al botón

Entiendo que en el modelo algo así estaba re mal, pero ¿en la vista si podemos tomarnos estas libertades?

Muchas Gracias!!

Saludos!

maguimarijuan commented 5 years ago

El la vista pueden tomarse esas libertades pero no abusen! JAJA! Es mejor usar instanceOf antes que el modelo tenga información de la vista.

Saludos!

lorenzolgz commented 5 years ago

jajajaja ay ¡menos mal! Buenísimo, lo hacemos con cautela

Gracias Magui! Saludos

lorenzolgz commented 5 years ago

Buenas noches Magui, quería contarte que estuvimos pensando con los chicos que hacer con la entrega del TP y llegamos a la conclusión de que si bien probablemente sigamos trabajando en él (porque tenemos ganas de terminarlo) estamos en una semana (y etapa del cuatri) bastante complicada (por ejemplo Gabi y Martin rinden el recu y yo tengo un final el martes) y no queremos comprometernos a un tiempo que no tenemos para dedicarle, de manera que seguro en unos días puedas chusmear algún que otro cambio (o hasta jugarlo si estas aburrida una tarde jaja) pero fuera de lo que compete a la materia y a esta cursada.

Además, sentimos que la nota final es representativa del esfuerzo puesto y no tenemos más que agradecimientos por toda la ayuda que nos diste a lo largo del desarrollo.

Saludos!

PD: Si todavía siguen en pie esos "tips" para el final, nos vienen muuuuy bien

maguimarijuan commented 5 years ago

Oki! Entonces cerramos en 7.5.

Tips para el final: -Leer la unidad de principios solid del libro de Fontela. -Saberse los principios solid DE ME MO RIA. Poder identificarlos. -Leer las lecturas obligatorias aunque sea una vez. -Tener un par de patrones de diseño bajo la manga. -Tener algún patrón creaciones bajo la manga, como aquel que menciona el libro de Fontela para crear un iterador asociado a una lista. -Practicar algún final antes.

Saludos! Mucha suerte!

Magui!

maguimarijuan commented 5 years ago

PD: Anótense al final, si pueden lleven la compu.

maguimarijuan commented 5 years ago

PD2: Todo lo que creen en el final acompáñenlos con sus pruebas unitarias. No olvidarse bajo ningún punto de TDD y de las buenas prácticas (atributos privados, métodos públicos, clases abstractas, pocos if y encapsulamiento aunque éste último es un solid).

maguimarijuan commented 5 years ago

PD3: No olviden que la Herencia es sólo para aquellos casos donde se reutiliza código y el objeto es el que hereda (sustitución de Liskov!!!!!)

maguimarijuan commented 5 years ago

PD 4: hagan bien los diagramas (con la notación UML), no se olviden del diagrama de estados, ejem ejem.

lorenzolgz commented 5 years ago

Muchas gracias Magui!!! Los vamos a aplicar

MartinDardis commented 5 years ago

Mil gracias magui!!

maguimarijuan commented 5 years ago

La nota les cerró con 8! Saludos!

MartinDardis commented 5 years ago

Hola magui, primero gracias por la nota!, te queria preguntar si tenes alguna recomendacion a la hora de encarar un modelo para el recu mañana, Hice parciales pero nunca termino de estar 100% seguro de si lo que hice esta bien o no.. Gracias, saludos

maguimarijuan commented 5 years ago

Mmmm, lo que les puedo sugerir es: -que se aseguren de que su modelo funcione. -que el comportamiento que tengan duda lo agreguen como supuesto. -hagan pruebas unitarias si les piden hacer pruebas.

maguimarijuan commented 5 years ago

Algunos chicos se equivocan porque hacen una explosión de clases. Fijense que todas sus clases tengan comportamiento y que no haya mucho acoplamiento.

maguimarijuan commented 5 years ago

Y como siempre, traten que su diagrama de secuencia se note la delegación! esto es lo más importante!!

MartinDardis commented 5 years ago

Joya, para el ejercicio de la sube, te parece bien que la tarjeta tenga sus viajes y un estado que calcule el descuento correspondiente?

ejemplo: int cobrarViaje(int costo, Date fecha) y que calcule ahi el descuenta o

int costoConDescuento = tarjeta.calcularDescuentoViaje(int costoBase);
tarjeta.cobrarViaje(int costoConDescuento, Date fecha);
maguimarijuan commented 5 years ago

el método calcular descuento viaje es un método privado? O alguien sabe que existe ese método? No se rompe un poco el encapsulamiento?

maguimarijuan commented 5 years ago

¿Qué opinas de un objeto interno que sepa el estado de los viajes, que se actualice con la fecha? #patronStateForEver. Después la tarjeta delega a este estado el cálculo del viaje.

MartinDardis commented 5 years ago

eso hice el recu pasado, una clase sistema que llevaba registro de los viajes y calculaba el descuento pero nose estaria bien?

maguimarijuan commented 5 years ago

Estaría bien siempre y cuando le pases la fecha, tendría que ver el modelo completo!

MartinDardis commented 5 years ago

mi supuesto era q la clase siempre sabia la fecha en la q estaba (tipo relos interno ? ), entonce llevaba un registro de viajes por tarjeta

maguimarijuan commented 5 years ago

mmm, me parece un supuesto muy fuerte!

MartinDardis commented 5 years ago

voy a arrancarlo de 0 de nuevo a ver que onda, por eso, no sabia donde meter los viajes si en tarjeta o en alguna otra clase aparte

maguimarijuan commented 5 years ago

dale! cuando termines mándame una foto y lo vemos

MartinDardis commented 5 years ago

Aca hice le diagrama de secuencias, una vez terminado pense q la parte de verificar si pude viajar podria evitarla y tan solo esperar una excepcion al cobrar ( de todos modo el enunciado dice que se verifica al inicio si hay saldo suficiente por eso lo deje)

sequence diagram0