Add Versioned, Recorded and FSM
This commit is contained in:
parent
ef746d69ba
commit
c95a809bfd
@ -1,7 +1,7 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFrameworks>net6.0; net48</TargetFrameworks>
|
||||
<TargetFrameworks>net6.0</TargetFrameworks>
|
||||
<RootNamespace>lib</RootNamespace>
|
||||
<AssemblyVersion>0.0.1.0</AssemblyVersion>
|
||||
<FileVersion>0.0.1.0</FileVersion>
|
||||
@ -25,7 +25,11 @@
|
||||
<ItemGroup>
|
||||
<Folder Include="Properties\" />
|
||||
<Folder Include="reflect\" />
|
||||
<Folder Include="fsm\" />
|
||||
</ItemGroup>
|
||||
|
||||
|
||||
<ItemGroup>
|
||||
<None Remove="fsm\" />
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
|
||||
61
fsm/FSM.cs
Normal file
61
fsm/FSM.cs
Normal file
@ -0,0 +1,61 @@
|
||||
|
||||
|
||||
using System;
|
||||
|
||||
|
||||
|
||||
namespace fsm;
|
||||
|
||||
|
||||
|
||||
public record class Context : imm.Recorded<Context>
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
public record class State<T, CTX> : imm.Recorded<State<T, CTX>>
|
||||
where T: State<T, CTX>
|
||||
where CTX: Context
|
||||
{
|
||||
virtual public (CTX, T) onEnter(CTX ctx, State<T, CTX> oldState)
|
||||
{
|
||||
return (ctx, (T)this);
|
||||
}
|
||||
|
||||
virtual public (CTX, T) onExit(CTX ctx, State<T, CTX> newState)
|
||||
{
|
||||
return (ctx, (T)this);
|
||||
}
|
||||
}
|
||||
|
||||
public record class FSM<T, CTX, ST> : imm.Recorded<FSM<T, CTX, ST>>
|
||||
where T: FSM<T, CTX, ST>
|
||||
where CTX: Context
|
||||
where ST: State<ST, CTX>
|
||||
{
|
||||
public CTX Context { get; private set; }
|
||||
public ST State { get; private set; }
|
||||
|
||||
public FSM(CTX context, ST state)
|
||||
{
|
||||
Context = context;
|
||||
State = state;
|
||||
}
|
||||
|
||||
public FSM<T, CTX, ST> Transition(ST newState)
|
||||
{
|
||||
var (newOldCTX, oldState) = State.onExit(Context, newState);
|
||||
|
||||
var (newCTX, storeState) = newState.onEnter(newOldCTX, oldState);
|
||||
|
||||
return this with
|
||||
{
|
||||
Context = newCTX,
|
||||
State = storeState,
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
87
imm/Imm.cs
87
imm/Imm.cs
@ -2,14 +2,93 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Collections.Immutable;
|
||||
using System.Linq;
|
||||
using System.Runtime.CompilerServices;
|
||||
using System.Text;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
// A spot for immutable helpers
|
||||
|
||||
public static class imm
|
||||
{
|
||||
|
||||
|
||||
namespace imm
|
||||
{
|
||||
public record class Versioned<T>
|
||||
where T: Versioned<T>
|
||||
{
|
||||
public uint Version { get; protected set; } = 0;
|
||||
public string Reason { get; protected set; } = "";
|
||||
|
||||
public T Process(Func<T, T> fn, string reason = "")
|
||||
{
|
||||
var newT = fn((T)this);
|
||||
|
||||
return newT with
|
||||
{
|
||||
Version = newT.Version + 1,
|
||||
Reason = reason,
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
public record class Recorded<T> : Versioned<T>
|
||||
where T : Recorded<T>
|
||||
{
|
||||
public T? Old { get; private set; }
|
||||
public string Expression { get; private set; } = "";
|
||||
public string MemberName { get; private set; } = "";
|
||||
public string FilePath { get; private set; } = "";
|
||||
public int LineNumber { get; private set; } = -1;
|
||||
|
||||
public T Record(string reason = "",
|
||||
[CallerMemberName] string memberName = "",
|
||||
[CallerFilePath] string filePath = "",
|
||||
[CallerLineNumber] int lineNumber = 0)
|
||||
{
|
||||
var orig = (T)this;
|
||||
|
||||
var newT = base.Process((old) => old with
|
||||
{
|
||||
Old = orig,
|
||||
MemberName = memberName,
|
||||
FilePath = filePath,
|
||||
LineNumber = lineNumber,
|
||||
}, reason);
|
||||
|
||||
return newT;
|
||||
}
|
||||
|
||||
|
||||
public T Process(Func<T, T> fn, string reason = "",
|
||||
[CallerMemberName] string memberName = "",
|
||||
[CallerFilePath] string filePath = "",
|
||||
[CallerLineNumber] int lineNumber = 0,
|
||||
[CallerArgumentExpression("fn")]
|
||||
string expression = default)
|
||||
{
|
||||
var orig = (T)this;
|
||||
|
||||
return (T)this with
|
||||
{
|
||||
//Do the Versioned code here
|
||||
Version = orig.Version + 1,
|
||||
|
||||
//Recorded
|
||||
Old = orig,
|
||||
Expression = expression,
|
||||
MemberName = memberName,
|
||||
FilePath = filePath,
|
||||
LineNumber = lineNumber,
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static class Util
|
||||
{
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
Loading…
Reference in New Issue
Block a user