1
votes

Calculer winrate avec boucle recur

0
nil
1
nil
1

0 commentaires

4 Réponses :


0
votes

Voici une solution avec réduire:

 {:wins 0
  :matches 0
  :percentage []}

Il s'agit donc ici de maintenir (et de mettre à jour) l'état du calcul jusqu'à présent. Nous faisons cela dans la carte qui est

(defn calc-winrate [matches]
  (let [total-matches (count matches)]
    (->> matches
         (map :result)
         (reduce (fn [{:keys [wins matches percentage] :as result} match]
                  (let [wins (+ wins match)
                        matches (inc matches)]
                    {:wins wins
                     :matches matches
                     :percentage (conj percentage (to-percentage wins matches))}))
                 {:wins 0 
                  :matches 0
                  :percentage []}))))

Les victoires contiendront les victoires jusqu'à présent, les matchs sont le nombre de matchs que nous avons analysés et le pourcentage est le pourcentage jusqu'à présent.


0 commentaires

0
votes
(defn calc-winrate2 [ x y ]
  (let [ {total :total r :wins  } x
        {re :result } y]
    (if (pos? re )
      {:total (inc total) :wins (inc r)}
      {:total (inc total) :wins r}
      )
    )
  )

(reductions calc-winrate2 {:total 0 :wins 0} [   {:result 0} {:result 1} {:result 0} {:result 1} {:result 1}])

0 commentaires

1
votes

Voici une solution paresseuse utilisant des réductions pour obtenir une séquence de totaux de gains en cours, et les transducteurs pour 1) joindre les nombres ronds avec les totaux en cours 2) diviser les paires 3) convertir les fractions en pourcentages:

(defn calc-win-rate [results]
  (->> results
       (map :result)
       (reductions +)
       (sequence
         (comp
           (map-indexed (fn [round win-total] [win-total (inc round)]))
           (map (partial apply /))
           (map #(* 100 %))
           (map float)))))

(calc-win-rate [{:result 0} {:result 1} {:result 0} {:result 1} {:result 1}])
=> (0.0 50.0 33.333332 50.0 60.0)


2 commentaires

Quand je convertis en vecteur avec (en [] j'obtiens chaque entrée sur une nouvelle ligne, une idée pourquoi?


@Olle voulez-vous dire que le résultat s'imprime sur plusieurs lignes dans la REPL? Cela est contrôlé par un paramètre REPL, voir cette question . Cela n'affecte pas la valeur du résultat, seulement la façon dont il est imprimé.



1
votes

Vous pouvez calculer les taux de victoire en cours comme suit:

=> (calc-winrate [{:result 0} {:result 1} {:result 0} {:result 1} {:result 1}])
(0.0 50.0 33.333332 50.0 60.0)

Par exemple,

(defn calc-winrate [matches]
  (map
    (comp float #(* 100 %) /)
    (reductions + (map :result matches))
    (rest (range))))

La carte fonctionne sur deux séquences:

  • (reductions + (map: result matches)) - le total cumulé des victoires;
  • (rest (range)))) - (1 2 3 ...) , le nombre correspondant de correspondances.

La fonction ping map , (comp float # (* 100%) /) ,

  • divise les éléments correspondants des séquences,
  • le multiplie par 100 et
  • le transforme en virgule flottante.


1 commentaires

Très belle utilisation de map avec plusieurs entrées de collection