CONNEXION
  • RetourJeux
    • Sorties
    • Hit Parade
    • Les + populaires
    • Les + attendus
    • Soluces
    • Tous les Jeux
    • Gaming
  • RetourActu Gaming
    • News
    • Astuces
    • Tests
    • Previews
    • Toute l'actu gaming
  • RetourBons plans
    • Bons plans
    • Bons plans Smartphone
    • Bons plans Hardware
    • Bons plans Image et Son
    • Bons plans Amazon
    • Bons plans Cdiscount
    • Bons plans Decathlon
    • Bons plans Fnac
    • Tous les Bons plans
  • RetourJVTech
    • Actus High-Tech
    • Intelligence Artificielle
    • Smartphones
    • Mobilité urbaine
    • Hardware
    • Image et son
    • Tutoriels
    • Tests produits High-Tech
    • Guides d'achat High-Tech
    • JVTech
  • RetourCulture
    • Actus Culture
    • Culture
  • RetourVidéos
    • A la une
    • Gaming Live
    • Vidéos Tests
    • Vidéos Previews
    • Gameplay
    • Trailers
    • Chroniques
    • Replay Web TV
    • Toutes les vidéos
  • RetourForums
    • Hardware PC
    • PS5
    • Switch 2
    • Xbox Series
    • Switch
    • Pokemon pocket
    • FC 25 Ultimate Team
    • League of Legends
    • Tous les Forums
  • PC
  • PS5
  • Xbox Series
  • Switch 2
  • PS4
  • One
  • Switch
  • iOS
  • Android
  • MMO
  • RPG
  • FPS
En ce moment Genshin Impact Valhalla Breath of the wild Animal Crossing GTA 5 Red dead 2
Liste des sujets

Aide Clojure Programming

ZelteHonor
ZelteHonor
Niveau 7
09 décembre 2014 à 17:41:40

Je suis en train d'apprendre le Clojure avec le livre Clojure Programming que je me suis acheter. Je suis a peu près au quart, mais je bloc sur un premier gros exemple que je ne comprends pas. C'est le Conway's game of life en Clojure non idiomatic. Voici le code.
(defn neighbours [[x y]] (for [dx [-1 0 1] dy [-1 0 1] :when (not= 0 dx dy)] [ (+ dx x) (+ dy y)])) (defn count-neighbours [board loc] (count (filter #(get-in board %) (neighbours loc))))
Je comprends quand même bien le corps de la fonction, mais je me dit que je vais voir pour ces 2 fonctions là avant.

Message édité le 09 décembre 2014 à 17:45:29 par ZelteHonor
Caletlog
Caletlog
Niveau 10
09 décembre 2014 à 20:53:48

Salut,

La fonction neighbours permet, comme son nom l'indique, de récupérer un vecteur comportement tous les voisins du point de coordonnée (x,y) (dans un vecteur).
Avec ça, on fait une boucle. Le premier vecteur passé à la macro for est la forme liante ; on assigne à l'élément local "dx" le vecteur [-1 0 1] et le même à l'élément local "dy". Ils représentent les directions à explorer (-1 et 1 sur un axe x, -1 et 1 sur un axe y, ça revient à dire une fois à gauche, une à droite, une en haut et une en bas).
La macro for permet de recevoir des conditions ; c'est le :when. Ici, on saute l'itération lorsque dx ET dy valent 0 en même temps (ça évite de se compter soi-même ; si on ne le faisait pas, on comptabiliserai la position d'origine du point, puisqu'on appliquerait une translation de (0,0) sur le point).
Enfin, le coeur de la boucle dit de renvoyer, à chaque itération, un vecteur. Tous les vecteurs seront `cons`ed à une liste vide pour être renvoyées à la fin. Pour chaque itération, on renvoie donc un vecteur à deux membres, chaque membre étant une position (x,y).

Au final, on se retrouve donc bien avec une liste de vecteurs de coordonnées de tous les voisins du point d'origine.

Pour la fonction count-neighbours, celle-ci compte le nombre de voisins réels sur le tableau de jeu.
Concrètement, la fonction précédente te renvoie un ensemble de points potentiellement voisins, elle se fiche de savoir s'ils existent. Si par exemple tu lui fournis en argument le point [0, 0], elle va te renvoyer 5 coordonnées qui ne sont pas sur le plateau (en considérant un plateau d'indices uniquement positifs).
Du coup, count-neighbors va vérifier s'ils existent. Elle prend en argument le tableau ("board") et la localisation du point intéressé. Examinons-là :

-> (filter #(get-in board %) (neighbours loc))
Décomposons cette première partie :

-> neighbours loc
Fonction précédente, on a une liste des voisins potentiels du point

Du coup, `filter` va appliquer à chaque élément de la liste retournée par `neighbours loc` la fonction `#(get-in board %)`. Si cette dernière renvoie vraie, on garde l'élément ; sinon on le jette.

-> #(get-in board %)
Du coup, cette fonction prend en argument (%) un vecteur contenant les coordonnées d'un point, et cherche si ce vecteur est contenu dans le plateau. Get-in est l'équivalent d'un 'get' pour les structures imbriquées, comme le tableau.

Au final, cette partie avec filter élimine donc tous les éléments retournés par la fonction neighbours qui ne sont pas réellement dans le tableau.
On enveloppe le tout dans un count, et on a donc bien le nombre total de voisins réels d'un point donné.

Voilà voilà :)

Caletlog
Caletlog
Niveau 10
09 décembre 2014 à 21:18:49

Woaw, désolé pour toutes les fautes, j'avais de la musique en même temps :(

(+ merde, on peut éditer que pour 30 secondes ou quoi ?)

ZelteHonor
ZelteHonor
Niveau 7
09 décembre 2014 à 22:41:41

Merci beaucoup! Sa semble tous de suite plus clair! J'avais bien compris ce que les fonctions faisaient, mais je tenais à comprendre comment. C'est parfois assez difficile à suivre. J'ai un peu de difficulté par moment. J'aime bien la programmation fonctionnel et je suis ravie d'Avoir quelqu'un à qui demander de l'aide. Donc merci beaucoup!

Si j'ai encore besoin d'aide je devrais faire un autre topic ou réutiliser celui-ci?

Caletlog
Caletlog
Niveau 10
09 décembre 2014 à 22:56:57

À mon avis tu vas encore buter sur la suite des implémentations non-idiomatique et sans doute aussi idiomatique du jeu de la vie (ils sont assez imbuvables, c'est normal ; t'auras la même chose avec la génération de labyrinthes, et après ça devrait se calmer :o)) ) donc tant qu'à faire autant rester ici plutôt que polluer le forum avec 40 topics, je pense.

Petite correction d'ailleurs que je viens de voir pour la fonction count-neighbours : on cherche à avoir le nombre de voisins sur le plateau et _vivants_, puisque c'est le jeu de la vie. Si j'ai bonne mémoire, l'auteur représente les cellules vides/mortes par un 'nil' dans son plateau, et celles occupées/vivantes par un keyword. Du coup, la fonction ne permet pas juste de savoir si l'argument qu'on lui passe est dans le tableau, elle vérifie aussi que son contenu est bien vivant (= existe), puisque le get-in va renvoyer le contenu de la cellule sélectionnée par le point passé en argument. Si elle est vide, elle va renvoyer 'nil' (son contenu), tout comme si elle n'existe pas (comportement par défaut de get-in), sinon elle renvoie le symbole, qui est donc une valeur truthy qui fait tilter le filter.

ZelteHonor
ZelteHonor
Niveau 7
10 décembre 2014 à 00:16:04

Ça c'est bon j'avais réussis a comprendre. Quand j'aurai le temps de continuer je reposterais ici alors.

Sous forums
  • Aide à l'achat Mac
  • Création de Jeux
  • Linux
  • Programmation
  • Création de sites web
  • Internet
  • Steam Deck
  • Macintosh
  • Hardware
La vidéo du moment