add model + stat drafts

dev_raz_wip
Laurent 7 years ago
parent a6230736a7
commit 4b10acce58
  1. 169
      app/src/main/java/net/pokeranalytics/android/Model.kt
  2. 12
      app/src/main/java/net/pokeranalytics/android/calculus/Aggregator.kt
  3. 109
      app/src/main/java/net/pokeranalytics/android/calculus/Calculator.kt
  4. 111
      app/src/main/java/net/pokeranalytics/android/calculus/Computable.kt
  5. 8
      app/src/main/java/net/pokeranalytics/android/calculus/Format.kt
  6. 65
      app/src/main/java/net/pokeranalytics/android/calculus/Stat.kt

@ -0,0 +1,169 @@
package net.pokeranalytics.android
import java.util.*
class Session(bankroll: Bankroll, timeFrame: TimeFrame) {
// A comment written by the user
var comment: String? = null
// The date of creation of the session
var creationDate: Date = Date()
var limit: Int? = null
var game: Game? = null
var numberOfTables: Int = 1
var tableSize: Int? = null
var bankroll: Bankroll = bankroll
var hands: List<HandHistory> = listOf()
var timeFrame: TimeFrame = timeFrame
var location: Location? = null
var result: Result = Result()
var opponents: List<Player> = listOf()
// @todo serie
// @todo cash game blind: 2/5/10, short deck ante, big bets in fixed limit
// Tournament
var entryFee: Double? = null
var numberOfPlayers: Int? = null
// @todo tournament type?
}
class TimeFrame {
var startDate: Date = Date()
var endDate: Date? = null
var breakDuration: Double = 0.0
var duration: Double = 0.0
var paused: Boolean = false
}
open class TimeFrameGroup(timeFrame: TimeFrame) {
var timeFrame: TimeFrame = timeFrame
var timeFrames: List<TimeFrame> = listOf()
}
class Serie(timeFrame: TimeFrame) : TimeFrameGroup(timeFrame) {
}
class Result {
var buyin: Double? = null
var cashout: Double? = null
var netResult: Double? = null
var net: Double? = null
var transactions: List<Transaction> = listOf()
// @todo tips?
var finalPosition: Int? = null
// var player: Player? = null
}
class Bankroll(name: String) {
var live: Boolean = true
var name: String = name
var transactions: List<Transaction> = listOf()
var currency: Currency? = null
// @todo rate management
}
class Currency {
var code: String? = null
var rate: Double? = null
}
class Transaction(value: Double, type: TransactionType) {
var value: Double = value
var date: Date = Date()
var comment: String? = null
var type: TransactionType = type
}
enum class TransactionKind {
WITHDRAWAL,
DEPOSIT
}
class TransactionType(name: String) {
var name: String = name
var additive: Boolean = false
var lock: Boolean = false
var kind: TransactionKind? = null
}
class Game(name: String) {
var name: String = name
var shortName: String? = null
}
class Location(name: String) {
var name: String = name
var longitude: Double? = null
var latitude: Double? = null
}
class TournamentType(name: String) {
var name: String = name
}
class Player {}
enum class ReportDisplay {
TABLE,
GRAPH,
MAP
}
class Report(name: String) {
var name: String = name
var display: ReportDisplay = ReportDisplay.TABLE
// @todo define the configuration options
var comparators: List<Int> = listOf()
var stats: List<Int> = listOf()
var filters: List<Filter> = listOf()
}
class Filter(name: String) {
var name: String = name
var usageCount: Int = 0
var components: List<FilterComponent> = listOf()
}
class FilterComponent {
// @todo how to store sub-filters?
}
class HandHistory {
// @todo
}
class CustomField {
// @todo
}

@ -0,0 +1,12 @@
package net.pokeranalytics.android.calculus
class AggregationParameter<T> {
var values: List<T>? = null
}
class Aggregator {
var parameters: List<AggregationParameter<*>> = listOf()
}

@ -0,0 +1,109 @@
package net.pokeranalytics.android.calculus
import net.pokeranalytics.android.Serie
class Calculator {
class Options {
enum class Display {
TABLE,
EVOLUTION,
COMPARISON,
MAP,
POLYNOMIAL
}
enum class EvolutionValues {
NONE,
STANDARD,
DATED
}
var display: Display = Display.TABLE
var evolutionValues: EvolutionValues = EvolutionValues.NONE
var displayedStats: List<Stat> = listOf()
// var aggregation: Aggregation? = null
}
companion object {
fun computePreAggregation(groups: List<SessionGroup>, options: Options): List<ComputedGroup> {
return listOf()
}
// Computes all stats for list of Session group
fun computeGroups(groups: List<SessionGroup>, options: Options): List<ComputedGroup> {
var computedGroups: MutableList<ComputedGroup> = mutableListOf()
groups.forEach { group ->
// Computes actual group stats
val results: ComputedResults = Calculator.compute(group, options = options)
// Computes the compared group if existing
val comparedGroup = group.comparedGroup
if (comparedGroup != null) {
val comparedResults = Calculator.compute(comparedGroup, options = options)
group.comparedComputedGroup = ComputedGroup(comparedGroup, comparedResults)
results.computeStatVariations(comparedResults)
}
results.finalize(options)
computedGroups.add(ComputedGroup(group, results))
}
return computedGroups
}
// Computes stats for a SessionGroup
fun compute(group: SessionGroup, options: Options) : ComputedResults {
val sessions: List<SessionInterface> = group.sessionGroup
val series: Set<Serie> = setOf() // @todo get unique list of serie
var results: ComputedResults = ComputedResults()
var sum: Double = 0.0
var duration: Double = 0.0
// @todo add all stats
// Compute for each session
sessions.forEach { item ->
sum += item.value
when (options.evolutionValues) {
Options.EvolutionValues.STANDARD -> {
results.addEvolutionValue(sum, Stat.NETRESULT)
}
Options.EvolutionValues.DATED -> {
results.addEvolutionValue(sum, duration, Stat.NETRESULT)
}
}
}
// Compute for each serie
series.forEach { serie ->
duration += serie.timeFrame.duration
if (options.evolutionValues != Options.EvolutionValues.NONE) {
results.addEvolutionValue(duration, Stat.DURATION)
}
}
// Create stats
results.addStats(setOf(
ComputedStat(Stat.NETRESULT, sum),
ComputedStat(Stat.AVERAGE,sum / sessions.size),
ComputedStat(Stat.DURATION, duration)
))
return results
}
}
}

@ -0,0 +1,111 @@
package net.pokeranalytics.android.calculus
import net.pokeranalytics.android.Serie
// An interface to describe objects that can be summed
interface Summable {
var value: Double
}
// An interface describing some class that can be computed
interface SessionInterface : Summable {
var serie: Serie
}
/**
* A group of computable items identified by a name
*/
class SessionGroup(name: String, sessions: List<SessionInterface>) {
var name: String = name
var sessionGroup: List<SessionInterface> = sessions
// A subgroup used to compute stat variation
var comparedGroup: SessionGroup? = null
// The computed stats of the comparable group
var comparedComputedGroup: ComputedGroup? = null
}
class ComputedGroup(group: SessionGroup, computedResults: ComputedResults) {
// A computable group
var group: SessionGroup = group
// The computed stats of the group
var computedResults: ComputedResults = computedResults
fun statValue(stat: Stat) : Double? {
return computedResults.computedStat(stat)?.value
}
}
class ComputedResults() {
// The computed stats of the group
private var _computedStats: MutableMap<Stat, ComputedStat> = mutableMapOf()
// The map containing all evolution values for all stats
private var _evolutionValues: MutableMap<Stat, MutableList<Point>> = mutableMapOf()
fun addEvolutionValue(value: Double, stat: Stat) {
this._addEvolutionValue(Point(value), stat = stat)
}
fun addEvolutionValue(value: Double, duration: Double, stat: Stat) {
this._addEvolutionValue(Point(value, y = duration), stat = stat)
}
private fun _addEvolutionValue(point: Point, stat: Stat) {
var evolutionValues = this._evolutionValues[stat]
if (evolutionValues != null) {
evolutionValues.add(point)
} else {
var values: MutableList<Point> = mutableListOf(point)
this._evolutionValues[stat] = values
}
}
fun addStats(computedStats: Set<ComputedStat>) {
computedStats.forEach {
this._computedStats[it.stat] = it
}
}
fun computedStat(stat: Stat) : ComputedStat? {
return this._computedStats[stat]
}
fun computeStatVariations(resultsToCompare: ComputedResults) {
this._computedStats.keys.forEach { stat ->
var computedStat = this.computedStat(stat)
val comparedStat = resultsToCompare.computedStat(stat)
if (computedStat != null && comparedStat != null) {
computedStat.variation = (computedStat.value - comparedStat.value) / comparedStat.value
}
}
}
fun finalize(options: Calculator.Options) {
if (options.evolutionValues != Calculator.Options.EvolutionValues.NONE) {
// Sort points as a distribution
this._computedStats.keys.filter { it.hasDistributionSorting() }.forEach { stat ->
// @todo sort
// var evolutionValues = this._evolutionValues[stat]
// evolutionValues.so
}
}
}
}
class Point(x: Double, y: Double) {
val x: Double = x
val y: Double = y
constructor(x: Double) : this(x, 1.0)
}

@ -0,0 +1,8 @@
package net.pokeranalytics.android.calculus
import android.graphics.Color
class StatFormat {
var text: String = ""
var color: Int = Color.BLUE
}

@ -0,0 +1,65 @@
package net.pokeranalytics.android.calculus
interface AnyStat {
}
enum class Stat : AnyStat {
NETRESULT,
HOURLYRATE,
DURATION,
AVERAGE,
STANDARDDEVIATION,
HOURLYSTANDARDDEVIATION;
fun label() : String = when (this) {
NETRESULT -> ""
HOURLYRATE -> ""
else -> throw IllegalArgumentException("Label not defined")
}
fun hasDistributionSorting() : Boolean {
when (this) {
STANDARDDEVIATION, HOURLYSTANDARDDEVIATION -> return true
else -> return false
}
}
}
enum class CashSessionStat : AnyStat {
NETBB,
AVERAGEBB
}
class ComputedStat(stat: Stat, value: Double) {
constructor(stat: Stat, value: Double, previousValue: Double?) : this(stat, value) {
if (previousValue != null) {
this.variation = (value - previousValue) / previousValue
}
}
// The statistic type
var stat: Stat = stat
// The stat value
var value: Double = value
// The variation of the stat
var variation: Double? = null
// The data points leading to the current stat value
// var points: List<Point> = mutableListOf()
// Formats the value of the stat to be suitable for display
fun format() : StatFormat {
return StatFormat()
}
fun evolutionValueFormat(index: Int) : StatFormat {
return StatFormat()
}
}
Loading…
Cancel
Save