-
Notifications
You must be signed in to change notification settings - Fork 5
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
[0.2.0] API Performance improvements and simulations (#12)
## UI - The Left Navigation Bar on Desktop has been revamped and will no longer scroll with the content. ## API - Instead of generating data per toughness, instead build `lt`, `eq`, `gt` properties. Then map that to the different toughness values (Fixes: #13) - This should have no difference in the final result, however, should improve performance greatly - If you try and generate data for attacks > 8, switch to a simulation of dice rolls rather than generating every permutation (Fixes: #13) - Added Sentry to API to capture errors (Fixes: #11) ## Notes Here is a table of the number of permutations as the attacks grow: | Attacks | Permutations | |---------|---------------| | 2 | 36 | | 4 | 1 296 | | 6 | 46 656 | | 8 | 1 679 616 | | 10 | 60 466 176 | | 12 | 2 176 782 336 | Because of this it becomes too expensive to get population permutations for attacks > 8. Hence why it switches over to doing `1 500 000` simulations instead. It should be accurate enough as the probabilities are limited to 2 dec. places on the UI anyway
- Loading branch information
Showing
30 changed files
with
776 additions
and
269 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,40 @@ | ||
export type TCount = { [damage: number]: number }; | ||
|
||
export interface ICounter { | ||
lt: TCount; | ||
eq: TCount; | ||
gt: TCount; | ||
} | ||
|
||
export class Counter implements ICounter { | ||
lt: TCount; | ||
eq: TCount; | ||
gt: TCount; | ||
|
||
constructor() { | ||
this.lt = {}; | ||
this.eq = {}; | ||
this.gt = {}; | ||
} | ||
|
||
increment(variant: keyof ICounter, damage: number) { | ||
this[variant][damage] = (this[variant][damage] || 0) + 1; | ||
} | ||
|
||
incrementLt(damage: number) { | ||
this.increment('lt', damage); | ||
} | ||
|
||
incrementEq(damage: number) { | ||
this.increment('eq', damage); | ||
} | ||
|
||
incrementGt(damage: number) { | ||
this.increment('gt', damage); | ||
} | ||
|
||
toDict(): ICounter { | ||
const { lt, eq, gt } = this; | ||
return { lt, eq, gt }; | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,78 @@ | ||
import 'core-js/stable'; | ||
import 'regenerator-runtime/runtime'; | ||
|
||
import { TVector } from 'api/types'; | ||
import { IGenerator } from 'js-combinatorics'; | ||
|
||
import { D6 } from './dice'; | ||
|
||
class SimulationGenerator implements IGenerator<TVector> { | ||
private generator: Generator<TVector, void, unknown>; | ||
private numSimulations: number; | ||
private numAttacks: number; | ||
length: number; | ||
|
||
constructor(numSimulations: number, numAttacks: number) { | ||
this.numSimulations = numSimulations; | ||
this.length = numSimulations; | ||
this.numAttacks = numAttacks; | ||
this.init(); | ||
} | ||
|
||
next(): TVector { | ||
const n = this.generator.next(); | ||
if (n.done) return undefined; | ||
return n.value as TVector; | ||
} | ||
|
||
forEach(f: (item: TVector) => void): void { | ||
this.init(); | ||
let n = this.next(); | ||
while (n) { | ||
f(n); | ||
n = this.next(); | ||
} | ||
this.init(); | ||
} | ||
|
||
map<TResult>(f: (item: TVector) => TResult): TResult[] { | ||
return this.toArray().map(f); | ||
} | ||
|
||
filter(predicate: (item: TVector) => boolean): TVector[] { | ||
this.init(); | ||
let n = this.next(); | ||
const result = []; | ||
while (n) { | ||
if (predicate(n)) result.push(n); | ||
n = this.next(); | ||
} | ||
this.init(); | ||
return result; | ||
} | ||
|
||
toArray() { | ||
this.init(); | ||
let n = this.next(); | ||
const result = []; | ||
while (n) { | ||
result.push(n); | ||
n = this.next(); | ||
} | ||
this.init(); | ||
return result; | ||
} | ||
|
||
private init() { | ||
this.generator = this.createGen(); | ||
} | ||
|
||
private *createGen(): Generator<TVector, undefined, TVector> { | ||
for (let i = 0; i < this.numSimulations; i += 1) { | ||
yield [...Array(this.numAttacks)].map(() => D6.roll()); | ||
} | ||
return undefined; | ||
} | ||
} | ||
|
||
export default SimulationGenerator; |
Oops, something went wrong.