Javaquarium

4 ans et 3 mois après, il est toujours là, et toujours aussi difficile !

a marqué ce sujet comme résolu.

Reprise du dernier message de la page précédente

Bonjour tout le monde :)

J'ai recommencé le Javaquarium, cette fois ci en Java. J'ai essayé de créer le dépôt directement depuis git, c'est la première fois que je fais ça donc c'était expérimentale mais j'ai bien un dépôt sur mon compte github, donc c'est que ça a du marcher: https://github.com/Nekyia/Javaquarium-2.git

Je n'ai pas encore fait la partie reproduction, mais j'ai un petit bug:

1
2
3
4
5
Exception in thread "main" java.util.ConcurrentModificationException
    at java.util.LinkedList$ListItr.checkForComodification(Unknown Source)
    at java.util.LinkedList$ListItr.next(Unknown Source)
    at Aquarium.tick(Simulation.java:191)
    at Simulation.main(Simulation.java:10)

Je n'ai pas encore vu ça (avant dernier chapitre de TIJ4 que je suis entrain d'étudier) donc un petit coup de pouce serait le bienvenue. J'attends aussi vos critiques sur mon code (mon bidouillage devrais-je dire). Notamment j'ai créé une classe interne DietBehavior pour distinguer les Herbivore des Carnivores et je fais appel à DietBehavior.eat() pour faire manger les poissons. Je ne sais pas ce que ça vaut comme solution. Pour rajouter une race, j'ai juste à rajouter la race dans le switch en lui donnant l'objet Diet adéquat. Je pensais faire la même chose pour la reproduction.

Comme d'habitude, merci d'avance !

+0 -0

Merci. J'ai trouvé une solution de contournement en utilisant un booléen isAlive. Mais comment faire sinon pour supprimer un poisson autre que celui retourné par l'itérateur, et comment supprimer depuis une autre méthode ? Il faut passer l'itérateur à la méthode qui va supprimer le poisson (eat()) ?

+0 -0

Je pense que le plus simple est de simplement modifier le booléen isAlive dans les méthodes et de nettoyer l'aquarium à chaque fin de "tour" dans la boucle principale (en utilisant une boucle comme dans le lien indiqué par Praetonus).

Édité par louk

+0 -0
Auteur du sujet

Parce que Kotlin c’est le langage à JVM qui monte, je tente mon propre exercice dans ce langage : https://github.com/SpaceFox/kotlinquarium – pour l’instant jusqu’à l’étape 2.1 qui pose des problèmes de modification concurrente rigolos si on y va naïvement.

À noter que c’est fait avec la doc sous la main, j’ai pour ainsi dire jamais codé dans ce langage avant. J’ai essayé d’être proche de ce que je perçois de la philosophie du langage Kotlin, quitte à m’éloigner de ce qu’on ferait en Java.

Édité par SpaceFox

Voici ma version en Ruby, c’est mon tout premier programme "sérieux" dans ce langage que je découvre depuis fin 2016 :)

Normalement toutes les étapes sont implémentées, avec quelques petits écarts cependant:

4.2/4.3 La sortie sur console est effectuée dans un format identique à celui du chargement, donc je n’ai pas prévu l’enregistrement dans un fichier séparé, la sortie console si elle est redirigée dans un fichier peut être réutilisée directement en entrée pour charger les êtres vivants

4.4 Au lieu d’être à part en entête, le tour initial est précisé pour chaque être vivant (c’est un attribut de la classe LivingBeing).

Quelques précisions supplémentaires:

  • Les espèces sont également chargées depuis un fichier, on peut donc en définir autant qu’on veut (animaux ou végétaux) avec des propriétés différentes (en terme de points de vie, longévité, valeur nutritive, etc).

  • J’ai rajouté également la gestion des omnivores (pour le fun et ça ne coûtait vraiment pas beaucoup plus cher à coder), donc au lieu d’avoir 7 comportements différents il y en a 10.

  • Le fichier public.txt contient un résumé des classes avec leurs attributs et méthodes publiques. Pour résumer il y 10 classes pour les espèces (classe de base Species) et 10 pour les êtres vivants (classe de base LivingBeing), j’utilise les mixins Ruby pour implémenter les différents comportements.

  • La correspondance entre la classe de l’espèce et la classe de l’être vivant et faite grâce une table de correspondance consultée lors du chargement des êtres vivants.

  • Un numéro séquentiel est utilisé pour nommer les nouveaux-nés

Un exemple de sortie pour un tour de simulation

#
# START OF TURN 7 - EVENTS
# Sepi 3 (Grouper, F) dies of starvation
#
# TURN 7 - EVENTS
# Tissol (Bass, M) attacks One Green Alga
# Rieuse 3 (Flounder, M) attacks One Red Alga
# Rieuse 4 (Flounder, F) attacks One Red Alga
# Enfant de Boheme (Murena, M) attacks Sepa (Grouper, M)
# 254 (Tuna, M) attacks One Red Alga
# 258 (Flounder, M) reproduces with Pleureuse 2 (Flounder, F)
# Their child is 260 (Flounder, F)
# Auguste (Clownfish, M) attacks Sepa 1 (Grouper, M)
# Amine 1 (Bass, F) attacks One Green Alga
# Eve 3 (Shark, F) attacks Diem 2 (Carp, M)
# Amine 2 (Bass, F) attacks One Green Alga
# Eve 4 (Shark, F) attacks Edonnay 4 (Tuna, M)
# Amine 3 (Bass, F) attacks One Red Alga
# Amine 4 (Bass, F) attacks One Green Alga
# Edonnay 3 (Tuna, M) reproduces with Tonelle 6 (Tuna, F)
# Their child is 261 (Tuna, F)
# Amine 7 (Bass, F) attacks One Green Alga
# Diem 1 (Carp, M) attacks One Red Alga
# La Muette 1 (Carp, F) attacks One Red Alga
# Edonnay 5 (Tuna, M) reproduces with 248 (Tuna, F)
# Their child is 262 (Tuna, F)
# Amine 9 (Bass, F) attacks One Red Alga
# Tonelle 2 (Tuna, F) attacks One Green Alga
# Sepi (Grouper, F) attacks Edonnay 2 (Tuna, M)
# La Muette 2 (Carp, F) attacks One Red Alga
# Edonnay 6 (Tuna, M) attacks One Red Alga
# Adam de la mer 4 (Shark, M) attacks Pleureuse (Flounder, M)
# La Muette 3 (Carp, F) attacks One Green Alga
# Edonnay 7 (Tuna, M) attacks One Red Alga
# La Muette (Carp, F) attacks One Red Alga
# La Muette 4 (Carp, F) attacks One Green Alga
# Sepa 4 (Grouper, M) attacks One Red Alga
# Ouille (Murena, M) attacks Sepi (Grouper, F)
# Diem 6 (Carp, M) attacks One Red Alga
# La Muette 6 (Carp, F) attacks One Red Alga
# La Muette 7 (Carp, F) attacks One Red Alga
# Sepa 5 (Grouper, M) attacks One Green Alga
# Diem 8 (Carp, M) attacks One Red Alga
# La Muette 8 (Carp, F) attacks One Green Alga
# Diem 9 (Carp, M) attacks One Green Alga
# Samba 3 (Piranha, F) attacks La Muette 6 (Carp, F)
# Tissol 1 (Bass, M) attacks One Green Alga
# La Muette 9 (Carp, F) attacks One Green Alga
# Sepa 7 (Grouper, M) attacks One Green Alga
# 247 (Flounder, M) attacks One Red Alga
# Tissol 2 (Bass, M) attacks One Green Alga
# Samba 5 (Piranha, F) attacks Tonelle 2 (Tuna, F)
# Pleureuse 1 (Flounder, F) attacks One Red Alga
# Tissol 4 (Bass, M) attacks One Red Alga
# Tissol 5 (Bass, M) attacks One Green Alga
# Pleureuse 3 (Flounder, F) attacks One Red Alga
# Tissol 6 (Bass, M) attacks One Red Alga
# Pleureuse 4 (Flounder, F) attacks One Green Alga
# Diem (Carp, M) attacks One Green Alga
# Tissol 7 (Bass, M) attacks One Red Alga
# Tissol 8 (Bass, M) attacks One Green Alga
# Rieuse 2 (Flounder, F) attacks One Red Alga
# Sepi 2 (Grouper, F) attacks One Red Alga
# 260 (Flounder, F) attacks One Red Alga
#
# END OF TURN 7 - STATE
#
# ANIMALS
#
# Species, Value, Initial turn, Age, Name, Sex
Carp, 10, 4, 4, 251, M
Bass, 11, 1, 7, Tissol 9, M
Bass, 5, 1, 7, Tissol, M
Flounder, 11, 1, 7, Rieuse 3, M
Tuna, 12, 4, 4, 252, F
Flounder, 11, 1, 7, Rieuse 4, F
Murena, 9, 1, 7, Enfant de Boheme, M
Grouper, 9, 1, 7, Sepi 4, F
Piranha, 11, 4, 4, 253, F
Tuna, 10, 4, 4, 254, M
Grouper, 9, 1, 7, Sepi 5, F
Murena, 1, 1, 7, Ouille 1, F
Grouper, 13, 5, 3, 255, M
Grouper, 9, 1, 7, Sepi 6, F
Murena, 8, 1, 7, Ouille 2, M
Shark, 10, 1, 7, Adam de la mer, M
Flounder, 12, 6, 2, 256, F
Grouper, 11, 1, 7, Sepi 7, F
Murena, 8, 6, 2, 257, F
Flounder, 10, 6, 2, 258, M
Clownfish, 12, 1, 7, Auguste, M
Clownfish, 9, 1, 7, Bozo 3, M
Carp, 10, 6, 2, 259, F
Clownfish, 10, 1, 7, Bozo, M
Flounder, 5, 1, 7, Pleureuse, M
Shark, 8, 1, 7, Eve 1, F
Grouper, 1, 1, 7, Sepa, M
Shark, 11, 1, 7, Eve 2, F
Bass, 13, 1, 7, Amine 1, F
Shark, 9, 1, 7, Eve 3, F
Bass, 13, 1, 7, Amine 2, F
Shark, 11, 1, 7, Eve 4, F
Bass, 11, 1, 7, Amine 3, F
Shark, 10, 1, 7, Eve 5, F
Tuna, 9, 1, 7, Edonnay, M
Bass, 13, 1, 7, Amine 4, F
Tuna, 11, 1, 7, Edonnay 1, M
Bass, 11, 1, 7, Amine 5, F
Piranha, 9, 1, 7, Samba, F
Tuna, 7, 1, 7, Edonnay 2, M
Bass, 11, 1, 7, Amine 6, F
Tuna, 8, 1, 7, Tonelle, F
Tuna, 11, 1, 7, Edonnay 3, M
Bass, 13, 1, 7, Amine 7, F
Shark, 12, 1, 7, Adam de la mer 1, M
Carp, 11, 1, 7, Diem 1, M
Tuna, 3, 1, 7, Edonnay 4, M
Bass, 11, 1, 7, Amine 8, F
Shark, 9, 1, 7, Adam de la mer 2, M
Tuna, 11, 1, 7, Tonelle 1, F
Bass, 11, 1, 7, Amine, F
Carp, 3, 1, 7, Diem 2, M
Carp, 7, 1, 7, La Muette 1, F
Tuna, 11, 1, 7, Edonnay 5, M
Bass, 11, 1, 7, Amine 9, F
Shark, 9, 1, 7, Adam de la mer 3, M
Tuna, 3, 1, 7, Tonelle 2, F
Grouper, 4, 1, 7, Sepi, F
Carp, 11, 1, 7, La Muette 2, F
Grouper, 9, 1, 7, 240, M
Tuna, 9, 1, 7, Edonnay 6, M
Grouper, 7, 1, 7, Sepa 1, M
Shark, 15, 1, 7, Adam de la mer 4, M
Tuna, 9, 1, 7, Tonelle 3, F
Carp, 11, 1, 7, Diem 3, M
Carp, 13, 1, 7, La Muette 3, F
Tuna, 9, 1, 7, 241, F
Tuna, 5, 1, 7, Edonnay 7, M
Carp, 11, 1, 7, La Muette, F
Shark, 9, 1, 7, Adam de la mer 5, M
Tuna, 10, 1, 7, Tonelle 4, F
Carp, 11, 1, 7, Diem 4, M
Carp, 11, 1, 7, La Muette 4, F
Tuna, 9, 1, 7, 242, M
Tuna, 13, 1, 7, Tonelle 5, F
Murena, 8, 1, 7, Enfant de Boheme 1, M
Flounder, 11, 1, 7, Rieuse, F
Carp, 11, 1, 7, La Muette 5, F
Flounder, 12, 2, 6, 243, M
Tuna, 9, 1, 7, Tonelle 6, F
Grouper, 9, 1, 7, Sepa 4, M
Murena, 9, 1, 7, Enfant de Boheme 2, M
Murena, 12, 1, 7, Ouille, M
Carp, 7, 1, 7, Diem 6, M
Carp, 5, 1, 7, La Muette 6, F
Bass, 10, 2, 6, 244, M
Tuna, 13, 1, 7, Tonelle 7, F
Carp, 11, 1, 7, Diem 7, M
Piranha, 12, 1, 7, Samba 1, F
Carp, 11, 1, 7, La Muette 7, F
Grouper, 11, 1, 7, Sepa 5, M
Shark, 11, 2, 6, 245, F
Carp, 7, 1, 7, Diem 8, M
Carp, 13, 1, 7, La Muette 8, F
Clownfish, 11, 1, 7, Auguste 1, M
Grouper, 11, 1, 7, Sepa 6, M
Carp, 12, 2, 6, 246, F
Carp, 13, 1, 7, Diem 9, M
Piranha, 5, 1, 7, Samba 3, F
Bass, 13, 1, 7, Tissol 1, M
Carp, 13, 1, 7, La Muette 9, F
Clownfish, 9, 1, 7, Auguste 2, M
Grouper, 12, 1, 7, Sepa 7, M
Flounder, 11, 3, 5, 247, M
Piranha, 9, 1, 7, Samba 4, F
Piranha, 13, 1, 7, Do Brasil 2, M
Bass, 9, 1, 7, Tissol 2, M
Clownfish, 9, 1, 7, Auguste 3, M
Tuna, 13, 3, 5, 248, F
Piranha, 14, 1, 7, Samba 5, F
Piranha, 10, 1, 7, Do Brasil 3, M
Flounder, 11, 1, 7, Pleureuse 1, F
Shark, 8, 4, 4, 249, M
Piranha, 9, 1, 7, Do Brasil 4, M
Bass, 11, 1, 7, Tissol 4, M
Flounder, 11, 1, 7, Pleureuse 2, F
Piranha, 9, 1, 7, Do Brasil 5, M
Bass, 13, 1, 7, Tissol 5, M
Flounder, 11, 1, 7, Pleureuse 3, F
Bass, 5, 1, 7, Tissol 6, M
Flounder, 13, 1, 7, Pleureuse 4, F
Carp, 13, 1, 7, Diem, M
Bass, 9, 1, 7, Tissol 7, M
Flounder, 11, 1, 7, Rieuse 1, F
Grouper, 9, 1, 7, Sepi 1, F
Tuna, 11, 4, 4, 250, F
Bass, 13, 1, 7, Tissol 8, M
Flounder, 11, 1, 7, Rieuse 2, F
Grouper, 9, 1, 7, Sepi 2, F
Flounder, 11, 7, 1, 260, F
Tuna, 9, 7, 1, 261, F
Tuna, 9, 7, 1, 262, F
#
# Animals count 132
#
# VEGETALS
#
# Species, Value, Initial turn, Age, Quantity
Red Alga, 9, 1, 7, 5
Red Alga, 13, 1, 7, 27
Green Alga, 15, 1, 7, 34
Green Alga, 11, 1, 7, 15
Green Alga, 17, 1, 7, 39
Green Alga, 7, 1, 7, 3
Red Alga, 5, 1, 7, 1
Red Alga, 17, 1, 7, 44
Red Alga, 11, 1, 7, 13
Green Alga, 13, 1, 7, 22
Green Alga, 9, 1, 7, 5
Red Alga, 15, 1, 7, 27
Green Alga, 5, 1, 7, 2
Red Alga, 7, 1, 7, 3
#
# Vegetals count 240

J’ai remarqué comme d’autres que les hermaphrodites opportunistes se multipliaient très vite, a priori ils ont 2 fois plus de chance de se reproduire donc j’en ai mis 2 fois moins au départ pour équilibrer l’évolution, du coup le "vainqueur" est assez souvent différent.

+1 -0

Ce pourrait être assez drôle de voir s’il est possible de trouver des équilibres dans cette population ^^. J’avais essayé de générer un modèle de Lotka-Voltera mais sans grand succès (faut dire que ma lib d’algo génétique était foireuse)

+0 -0

Salut,

J’ai tenté l’exercice en R avec des classes S3, ce qui s’est avéré peu pratique puisque ce genre de classe empêche la modification d’un objet. Du coup, a chaque fois qu’une opération modifiant l’aquarium est effectué, la totalité de l’aquarium est recopié puis l’ancienne version est écrasée. Utiliser des classe de type ReferenceClass, qui fonctionnent de la même façon qu’en Java, C# ou C++, aurait sans doute été plus simple (et oui, car en R il y a plusieurs style de programmation objet).

Je me suis arrêté à la partie 3.2 (La reproduction), la suite arrivera peut être, peut être pas. Quoi qu’il en soit vous pouvez trouver le code ici sous la forme d’un package R. Vous pouvez l’installer avec devtools::install_bitbucket("gcaillaut/raquarium") après avoir préalablement installé le package devtools avec install.packages("devtools").

Il y a un example d’aquarium que vous pouvez charger avec data(sample_aquarium), si vous voulez créez le votre, il y a un exemple de script de création dans le dossure data-raw/.

Un exemple d’utilisation ressemblerait à ça :

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
library(Raquarium)

data(sample_aquarium)

step0 <- sample_aquarium
step1 <- next_step(step0)
step2 <- next_step(step1)
# ...
# stepN <- next_step(stepN-1)

# Si on veut sauvegarder un aquarium
save(step2, file = "step2.Rda") # Créer un fichier step2.Rda
load("step2.Rda") # Pour charger le fichier step2.Rda (construit la variable step2)
+0 -0
Connectez-vous pour pouvoir poster un message.
Connexion

Pas encore membre ?

Créez un compte en une minute pour profiter pleinement de toutes les fonctionnalités de Zeste de Savoir. Ici, tout est gratuit et sans publicité.
Créer un compte