Optimize score variables.
This commit is contained in:
@@ -1,7 +1,10 @@
|
|||||||
using Cryville.Common;
|
using Cryville.Common;
|
||||||
|
using Cryville.Common.Buffers;
|
||||||
using Cryville.Common.Pdt;
|
using Cryville.Common.Pdt;
|
||||||
using Cryville.Crtr.Event;
|
using Cryville.Crtr.Event;
|
||||||
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
using System.Globalization;
|
||||||
|
|
||||||
namespace Cryville.Crtr {
|
namespace Cryville.Crtr {
|
||||||
public class Judge {
|
public class Judge {
|
||||||
@@ -30,14 +33,7 @@ namespace Cryville.Crtr {
|
|||||||
public Judge(PdtRuleset rs) {
|
public Judge(PdtRuleset rs) {
|
||||||
_etor = ChartPlayer.etor;
|
_etor = ChartPlayer.etor;
|
||||||
_rs = rs;
|
_rs = rs;
|
||||||
foreach (var s in rs.scores) {
|
InitScores();
|
||||||
var key = s.Key;
|
|
||||||
scoreSrcs.Add(key.Key, new PropSrc.Float(() => scores[key.Key]));
|
|
||||||
scoreOps.Add(key.Key, new PropOp.Float(v => scores[key.Key] = v));
|
|
||||||
scoreFmtKeys.Add(key.Key, IdentifierManager.SharedInstance.Request("_score_" + (string)key.Name));
|
|
||||||
scoreDefs.Add(key.Key, s.Value);
|
|
||||||
scores.Add(key.Key, s.Value.init);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
public void Prepare(float st, float et, Identifier input, JudgeDefinition def, ContainerState container) {
|
public void Prepare(float st, float et, Identifier input, JudgeDefinition def, ContainerState container) {
|
||||||
List<JudgeEvent> list;
|
List<JudgeEvent> list;
|
||||||
@@ -166,42 +162,95 @@ namespace Cryville.Crtr {
|
|||||||
var key = scoreop.Key;
|
var key = scoreop.Key;
|
||||||
_etor.ContextSelfValue = scoreSrcs[key.name.Key];
|
_etor.ContextSelfValue = scoreSrcs[key.name.Key];
|
||||||
_etor.Evaluate(scoreOps[key.name.Key], scoreop.Value);
|
_etor.Evaluate(scoreOps[key.name.Key], scoreop.Value);
|
||||||
scoreSrcs[key.name.Key].Invalidate();
|
InvalidateScore(key.name.Key);
|
||||||
foreach (var s in _rs.scores) {
|
foreach (var s in _rs.scores) {
|
||||||
if (s.Value.value != null) {
|
if (s.Value.value != null) {
|
||||||
_etor.ContextSelfValue = scoreSrcs[s.Key.Key];
|
_etor.ContextSelfValue = scoreSrcs[s.Key.Key];
|
||||||
_etor.Evaluate(scoreOps[s.Key.Key], s.Value.value);
|
_etor.Evaluate(scoreOps[s.Key.Key], s.Value.value);
|
||||||
scoreSrcs[s.Key.Key].Invalidate();
|
InvalidateScore(s.Key.Key);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ScoreCache.Clear();
|
|
||||||
}
|
}
|
||||||
readonly Dictionary<int, int> scoreFmtKeys = new Dictionary<int, int>();
|
readonly Dictionary<int, int> scoreStringKeys = new Dictionary<int, int>();
|
||||||
|
readonly Dictionary<int, int> scoreStringKeysRev = new Dictionary<int, int>();
|
||||||
readonly Dictionary<int, PropSrc> scoreSrcs = new Dictionary<int, PropSrc>();
|
readonly Dictionary<int, PropSrc> scoreSrcs = new Dictionary<int, PropSrc>();
|
||||||
readonly Dictionary<int, PropOp> scoreOps = new Dictionary<int, PropOp>();
|
readonly Dictionary<int, PropOp> scoreOps = new Dictionary<int, PropOp>();
|
||||||
readonly Dictionary<int, ScoreDefinition> scoreDefs = new Dictionary<int, ScoreDefinition>();
|
readonly Dictionary<int, ScoreDefinition> scoreDefs = new Dictionary<int, ScoreDefinition>();
|
||||||
public readonly Dictionary<int, float> scores = new Dictionary<int, float>();
|
readonly Dictionary<int, float> scores = new Dictionary<int, float>();
|
||||||
readonly Dictionary<int, string> ScoreCache = new Dictionary<int, string>();
|
readonly Dictionary<int, string> scoreStringCache = new Dictionary<int, string>();
|
||||||
readonly object _lock = new object();
|
readonly Dictionary<int, PropSrc> scoreStringSrcs = new Dictionary<int, PropSrc>();
|
||||||
public Dictionary<int, string> GetFormattedScoreStrings() {
|
readonly ArrayPool<byte> scoreStringPool = new ArrayPool<byte>();
|
||||||
lock (_lock) {
|
void InitScores() {
|
||||||
if (ScoreCache.Count == 0) {
|
foreach (var s in _rs.scores) {
|
||||||
foreach (var s in scores)
|
var key = s.Key.Key;
|
||||||
ScoreCache.Add(scoreFmtKeys[s.Key], s.Value.ToString(scoreDefs[s.Key].format));
|
var strkey = IdentifierManager.SharedInstance.Request("_score_" + (string)s.Key.Name);
|
||||||
}
|
scoreStringKeys.Add(key, strkey);
|
||||||
return ScoreCache;
|
scoreStringKeysRev.Add(strkey, key);
|
||||||
|
scoreSrcs.Add(key, new PropSrc.Float(() => scores[key]));
|
||||||
|
scoreOps.Add(key, new PropOp.Float(v => scores[key] = v));
|
||||||
|
scoreDefs.Add(key, s.Value);
|
||||||
|
scores.Add(key, s.Value.init);
|
||||||
|
scoreStringCache.Add(scoreStringKeys[key], null);
|
||||||
|
scoreStringSrcs.Add(scoreStringKeys[key], new ScoreStringSrc(scoreStringPool, () => GetScoreString(strkey)));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
void InvalidateScore(int key) {
|
||||||
|
scoreSrcs[key].Invalidate();
|
||||||
|
scoreStringCache[scoreStringKeys[key]] = null;
|
||||||
|
scoreStringSrcs[scoreStringKeys[key]].Invalidate();
|
||||||
|
}
|
||||||
|
string GetScoreString(int key) {
|
||||||
|
var result = scoreStringCache[key];
|
||||||
|
if (result == null) {
|
||||||
|
var rkey = scoreStringKeysRev[key];
|
||||||
|
return scoreStringCache[key] = scores[rkey].ToString(scoreDefs[rkey].format, CultureInfo.InvariantCulture);
|
||||||
|
}
|
||||||
|
else return result;
|
||||||
|
}
|
||||||
|
public bool TryGetScoreSrc(int key, out PropSrc value) {
|
||||||
|
return scoreSrcs.TryGetValue(key, out value);
|
||||||
|
}
|
||||||
|
public bool TryGetScoreStringSrc(int key, out PropSrc value) {
|
||||||
|
return scoreStringSrcs.TryGetValue(key, out value);
|
||||||
|
}
|
||||||
public string GetFullFormattedScoreString() {
|
public string GetFullFormattedScoreString() {
|
||||||
bool flag = false;
|
bool flag = false;
|
||||||
string result = "";
|
string result = "";
|
||||||
foreach (var s in GetFormattedScoreStrings()) {
|
foreach (var s in scores.Keys) {
|
||||||
result += string.Format(flag ? "\n{0}: {1}" : "{0}: {1}", IdentifierManager.SharedInstance.Retrieve(s.Key), s.Value);
|
result += string.Format(flag ? "\n{0}: {1}" : "{0}: {1}", IdentifierManager.SharedInstance.Retrieve(s), GetScoreString(scoreStringKeys[s]));
|
||||||
flag = true;
|
flag = true;
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
class ScoreStringSrc : PropSrc {
|
||||||
|
readonly Func<string> _cb;
|
||||||
|
readonly ArrayPool<byte> _pool;
|
||||||
|
byte[] _buf;
|
||||||
|
public ScoreStringSrc(ArrayPool<byte> pool, Func<string> cb) {
|
||||||
|
_pool = pool;
|
||||||
|
_cb = cb;
|
||||||
|
}
|
||||||
|
public override void Invalidate() {
|
||||||
|
base.Invalidate();
|
||||||
|
if (_buf != null) {
|
||||||
|
_pool.Return(_buf);
|
||||||
|
_buf = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
protected override unsafe void InternalGet(out int type, out byte[] value) {
|
||||||
|
var src = _cb();
|
||||||
|
int strlen = src.Length;
|
||||||
|
type = PdtInternalType.String;
|
||||||
|
value = _pool.Rent(sizeof(int) + strlen * sizeof(char));
|
||||||
|
fixed (byte* _ptr = value) {
|
||||||
|
char* ptr = (char*)(_ptr + sizeof(int));
|
||||||
|
*(int*)_ptr = strlen;
|
||||||
|
int i = 0;
|
||||||
|
foreach (var c in src) ptr[i++] = c;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
public class InputDefinition {
|
public class InputDefinition {
|
||||||
public int dim;
|
public int dim;
|
||||||
|
@@ -23,8 +23,6 @@ namespace Cryville.Crtr {
|
|||||||
else {
|
else {
|
||||||
var id = new Identifier(name);
|
var id = new Identifier(name);
|
||||||
PropSrc prop;
|
PropSrc prop;
|
||||||
string str;
|
|
||||||
float num;
|
|
||||||
if (ContextEvent != null && ContextEvent.PropSrcs.TryGetValue(name, out prop)) {
|
if (ContextEvent != null && ContextEvent.PropSrcs.TryGetValue(name, out prop)) {
|
||||||
prop.Get(out type, out value);
|
prop.Get(out type, out value);
|
||||||
}
|
}
|
||||||
@@ -32,15 +30,12 @@ namespace Cryville.Crtr {
|
|||||||
var vec = ContextState.GetRawValue(id);
|
var vec = ContextState.GetRawValue(id);
|
||||||
new VectorSrc(() => vec).Get(out type, out value);
|
new VectorSrc(() => vec).Get(out type, out value);
|
||||||
}
|
}
|
||||||
else if (ContextJudge != null && ContextJudge.scores.TryGetValue(name, out num)) {
|
else if (ContextJudge != null && ContextJudge.TryGetScoreSrc(name, out prop)) {
|
||||||
type = PdtInternalType.Number;
|
prop.Get(out type, out value);
|
||||||
LoadNum(num);
|
|
||||||
value = _numbuf;
|
|
||||||
RevokePotentialConstant();
|
RevokePotentialConstant();
|
||||||
}
|
}
|
||||||
else if (ContextJudge != null && ContextJudge.GetFormattedScoreStrings().TryGetValue(name, out str)) {
|
else if (ContextJudge != null && ContextJudge.TryGetScoreStringSrc(name, out prop)) {
|
||||||
type = PdtInternalType.String;
|
prop.Get(out type, out value);
|
||||||
value = GetBytes(str);
|
|
||||||
RevokePotentialConstant();
|
RevokePotentialConstant();
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
|
@@ -6,7 +6,7 @@ namespace Cryville.Crtr {
|
|||||||
public abstract class PropSrc {
|
public abstract class PropSrc {
|
||||||
int _type;
|
int _type;
|
||||||
byte[] _buf = null;
|
byte[] _buf = null;
|
||||||
public void Invalidate() { _buf = null; }
|
public virtual void Invalidate() { _buf = null; }
|
||||||
public void Get(out int type, out byte[] value) {
|
public void Get(out int type, out byte[] value) {
|
||||||
if (_buf == null) InternalGet(out _type, out _buf);
|
if (_buf == null) InternalGet(out _type, out _buf);
|
||||||
type = _type;
|
type = _type;
|
||||||
|
Reference in New Issue
Block a user