C# State Machine state change delegation - c#

I have been trying to build my own generic state machine but I can't figure out a way to tie state changes with events.
For now my generic implementation looks like this:
public interface IStateRoot
{
}
public interface IState<T> where T: IStateRoot
{
}
public abstract class State<T> : IState<T> where T: IStateRoot
{
public delegate void OnChange(IState<T> state);
OnChange OnStateChange;
public void Invoke()
{
OnStateChange?.Invoke(this);
}
}
public class FSM<T> where T: IStateRoot
{
public delegate void TransitionDelegate<K>(IState<K> state) where K: T;
public Dictionary<Type, TransitionDelegate<T>> Transitions;
public State<T> State { get; set; }
public FSM()
{
Transitions = new Dictionary<Type, TransitionDelegate<T>>();
}
public FSM(State<T> init)
{
Transition(init);
}
public void Transition<K>(K nextState) where K : State<T>
{
if (Transitions.TryGetValue(typeof(K), out var value))
{
value?.Invoke(nextState);
}
State = nextState;
}
public void OnTransition<K>(State<K>.OnChange action) where K : T
{
if (Transitions.TryGetValue(typeof(K), out var value))
{
value += action;
return;
}
Transitions.Add(typeof(K), action);
}
}
In a perfect world I would like to be able to create my own StateRoot and his States like this
public class MyState : IStateRoot
{
public class InitState : State<MyState> { }
public class EndState : State<MyState> { }
}
And then use it like this
public class StateListener
{
public FSM<MyState> StateMachine;
public StateListener()
{
StateMachine = new FSM<MyState>();
StateMachine.OnTransition<MyState.InitState>(OnInit);
StateMachine.OnTransition<MyState.EndState>(OnEndState);
StateMachine.Transition(new MyState.InitState());
}
public void OnEndState(MyState.EndState state)
{
Console.WriteLine("EndState");
}
public void OnInit(MyState.InitState state)
{
Console.WriteLine("StartState");
}
}
I'm having a problem with hooking generic methods to OnTransition.
The issue I'm having is that I can't convert from State<K>.OnChange to FSM<T>.TransitionDelegate<K> in OnTransitionMethod. I don't know how to go about it.

Related

Invoke parent function in derived nested class

How to invoke function Run() from Controller class in class I2C?
class Program
{
public class Controller
{
public void Run()
{
}
}
public class ChildController : Controller
{
}
public class LowLevelController : ChildController
{
private class I2C
{
public I2C()
{
}
// Want to call Controller.Run() from this level
}
public void Computate()
{
base.Run();
}
}
}
Option 1
One way to achieve this would be exposing method in I2C which accepts an Action. This would allow the instance of I2C, which is a private class defined within LowLevelController to invoke Controller.Run. For example,
private class I2C
{
public I2C()
{
}
public void RunBase(Action execute)
{
execute.Invoke();
}
}
Now you could execute the RunBase as
public void Computate()
{
var i2c = new I2C();
i2c.RunBase(()=>base.Run());
}
Option 2
The other option would be to pass an instance of LowLevelController to I2C and invoke the Controller.Run method
Example,
public class LowLevelController : ChildController
{
private class I2C
{
private LowLevelController _parent;
public I2C(LowLevelController parent)
{
_parent = parent;
}
public void RunBase()
{
_parent.Run();
}
}
public void Computate()
{
var i2c = new I2C(this);
i2c.RunBase();
}
}
I think what you want is simply:
public class LowLevelController : ChildController {
private class I2C {
public I2C(LowLevelController outerInstance) {
OuterInstance = outerInstance;
}
private LowLevelController OuterInstance { get; }
private void DoSomething() {
OuterInstance.Run();
}
}
}

how to resolve a type safe collection in the constructor?

I have this object structure
public interface IHandler<in TMessage>
{
void HandleMessage(TMessage messageType);
}
public class MessageType1
{
}
public class MessageType2
{
}
public class HandlerMessageType1 : IHandler<MessageType1>
{
public void HandleMessage(T messageType)
{
}
}
public class HandlerMessageType2 : IHandler<MessageType2>
{
public void HandleMessage(T messageType)
{
}
}
and the registration
container.Collection.Register(typeof(IHandler<>), new[]
{
typeof(HandlerMessageType1),
typeof(HandlerMessageType2)
});
how the constructor of the class where this is injected should look like?
public class ClientClass
{
public ClientClass(IEnumerable<IHandler<>> handlers)
{
}
}
like this doesn't work... how the signature of the client class constructor should look like?
this was edited to improve the example.
tkx in advance
Paulo Aboim Pinto
I Know if I understood, but with unity you can have:
public class Handler1 : IHandler
{
public void HandlerType()
{
Console.WriteLine("Handler1");
}
}
public class Handler2 : IHandler
{
public void HandlerType()
{
Console.WriteLine("Handler2");
}
}
public interface IHandler
{
void HandlerType();
}
Unity configuration
public static class DependencyConfiguration
{
public static UnityContainer Config()
{
var unity = new UnityContainer();
unity.RegisterType<IHandler, Handler1>("Handler1");
unity.RegisterType<IHandler, Handler2>("Handler2");
unity.RegisterType<IEnumerable<IHandler>>();
return unity;
}
}
A class to resolve:
public class ListOfTypes
{
private List<IHandler> handlers;
public ListOfTypes(IEnumerable<IHandler> handlers)
{
this.handlers = handlers.ToList();
}
public void PrintHandlers()
{
handlers.ForEach(_ => _.HandlerType());
}
}
The program:
static void Main(string[] args)
{
Console.WriteLine("Resolve sample");
var unity = DependencyConfiguration.Config();
var lstOfTypes = unity.Resolve<ListOfTypes>();
lstOfTypes.PrintHandlers();
Console.ReadLine();
}
Result:

Generics cannot explicitly convert type

For background I mainly program in Java and am trying to work with/learn generics in a C# project and got stuck.
Here is my problem. From the main method you can see I am trying to set the soldiers task, but I'm getting the error,
cannot convert from 'TaskHeal' to 'TaskBase<SoldierBase>'
It seems that this cast should work as TaskHeal is a child of TaskBase, but it doesn't. Here is my complete code:
public class Main {
static void main(string[] args) {
SoldierMedic myMedic = new SoldierMedic();
myMedic.setTask(new TaskHeal(myMedic)); // Problem!
}
}
public class SoldierBase {
private TaskBase<SoldierBase> currentTask;
public int status;
public void setTask(TaskBase<SoldierBase> newTask) {
this.currentTask = newTask;
}
}
public class SoldierMedic : SoldierBase {
public int healRate = 45;
}
public abstract class TaskBase<T> where T : SoldierBase {
protected T soldier;
public TaskBase(T unit) {
this.soldier = unit;
this.soldier.status = 1;
}
public abstract void preformTask();
}
public class TaskHeal : TaskBase<SoldierMedic> {
public TaskHeal(SoldierMedic unit) : base(unit) { }
public override void preformTask() {
this.soldier.healRate++;
}
}
If you don't mind having an additional base, non-generic class for TaskBase and SoldierBase, you could do this:
class Program
{
static void Main(string[] args)
{
var myMedic = new SoldierMedic();
myMedic.setTask(new TaskHeal(myMedic)); // Problem!
}
}
public class SoldierBase
{
public int status;
}
public class SoldierBase<T> : SoldierBase where T : SoldierBase
{
private TaskBase currentTask;
public void setTask(TaskBase newTask)
{
this.currentTask = newTask;
}
}
public class SoldierMedic : SoldierBase<SoldierMedic>
{
public int healRate = 45;
}
public abstract class TaskBase
{
}
public abstract class TaskBase<T> : TaskBase where T : SoldierBase<T>
{
protected T soldier;
public TaskBase(T unit)
{
this.soldier = unit;
this.soldier.status = 1;
}
public abstract void preformTask();
}
public class TaskHeal : TaskBase<SoldierMedic>
{
public TaskHeal(SoldierMedic unit) : base(unit) { }
public override void preformTask()
{
this.soldier.healRate++;
}
}
If you want this to look more like c# (using properties, proper access modifiers and casing), you'd do something like this:
class Program
{
static void Main(string[] args)
{
var myMedic = new SoldierMedic();
myMedic.CurrentTask = new TaskHeal(myMedic); // Problem!
}
}
public class SoldierBase
{
public int Status { get; set; }
}
public class SoldierBase<T> : SoldierBase where T : SoldierBase
{
public TaskBase CurrentTask { get; set; }
}
public class SoldierMedic : SoldierBase<SoldierMedic>
{
public int HealRate { get; set; } = 45;
}
public abstract class TaskBase
{
}
public abstract class TaskBase<T> : TaskBase where T : SoldierBase<T>
{
protected T Soldier;
public TaskBase(T unit)
{
Soldier = unit;
Soldier.Status = 1;
}
public abstract void PerformTask();
}
public class TaskHeal : TaskBase<SoldierMedic>
{
public TaskHeal(SoldierMedic unit) : base(unit) { }
public override void PerformTask()
{
Soldier.HealRate++;
}
}

Abstract factory implementation within C# application

I'd like to implement abstract factory design pattern. I add this snippet :
public class Class1
{
static Ete _ete;
static Hiver _hiver;
public static void Main(Clothes cl)
{
_ete = cl.CreateEteClothes();
_hiver = cl.CreateHiverClothes();
Console.WriteLine(_ete.GetMarque());
Console.ReadKey();
Console.WriteLine(_hiver.GetMarque());
Console.ReadKey();
}
}
public abstract class Clothes
{
public abstract Ete CreateEteClothes();
public abstract Hiver CreateHiverClothes();
}
public abstract class ItalianFactory: Clothes
{
public override Ete CreateEteClothes()
{
return new TShirtJuve();
}
public override Hiver CreateHiverClothes()
{
return new PullJuve();
}
}
public abstract class FrenchFactory : Clothes
{
public override Ete CreateEteClothes()
{
return new TShirtPsg();
}
public override Hiver CreateHiverClothes()
{
return new PullPsg();
}
}
public abstract class TunisianFactory : Clothes
{
public override Ete CreateEteClothes()
{
return new TShirtCa();
}
public override Hiver CreateHiverClothes()
{
return new PullCa();
}
}
public abstract class Ete
{
public abstract string GetMarque();
}
public abstract class Hiver
{
public abstract string GetMarque();
}
public class TShirtJuve: Ete
{
public override string GetMarque()
{
return "Juventus T shirt";
}
}
public class TShirtPsg : Ete
{
public override string GetMarque()
{
return "PSG T shirt";
}
}
public class TShirtCa : Ete
{
public override string GetMarque()
{
return "club africain T shirt";
}
}
public class PullJuve : Hiver
{
public override string GetMarque()
{
return "Juventus Pull";
}
}
public class PullPsg : Hiver
{
public override string GetMarque()
{
return "PSg Pull";
}
}
public class PullCa : Hiver
{
public override string GetMarque()
{
return "Club africain Pull";
}
}
I'd like to test this implementation, but I get an exception indicates that the signature of main method is not acceptable.
So How can I fix my code to test this design pattern implementation?
You have public static void Main(Clothes cl)
This should be static void Main(string[] args) as this is the entry point for the application and there can be only one entry point. See the .NET documentation for more info.
A method's signature usually consists of the methods name, return type, and parameters. Your application is expecting the correct signature for the Main method, hence it's giving you this exception.

Is there a standard pattern for creating worker classes with access to protected members?

I just did something kind of wacky using a partial class and I'm wondering if there's an already established pattern that might have accomplished the same thing using a less confusing approach.
The problem:
I had a base class with protected members and virtual methods designed for the derived class to do work when they are called.
I wanted to delegate this work out to a list of workers.
However I needed the workers to have access to the protected members.
My probably overly complicated solution:
Note: I realize this depends on the class being partial - I'm OK with that but it would be cool if there was a solution that didn't need it...
void Main()
{
ABase aBase = new ADerived();
aBase.DoWork();
}
public partial class ABase
{
protected int state1 = 1;
protected int state2 = 2;
List<ABase> workers;
public ABase()
{
workers = new List<ABase>();
CreateWorkers(workers);
}
protected virtual void CreateWorkers(List<ABase> workers)
{
}
public ABase(ABase aBase)
{
this.Target = aBase;
}
public virtual void DoWork()
{
foreach (var worker in this.workers)
{
worker.DoWork();
}
}
protected ABase Target { get; private set; }
}
public partial class ABase
{
public class Worker1 : ABase
{
public Worker1(ABase aBase) : base(aBase) { }
public override void DoWork()
{
Console.WriteLine (Target.state1);
}
}
public class Worker2 : ABase
{
public Worker2(ABase aBase) : base(aBase) { }
public override void DoWork()
{
Console.WriteLine (Target.state2);
}
}
}
public class ADerived : ABase
{
protected override void CreateWorkers(List<ABase> workers)
{
workers.Add(new Worker1(this));
workers.Add(new Worker2(this));
}
}
Output:
1
2
I would change the design so that the workers weren't accessing instance fields at all. I would have DoWork take a parameter with the information that they need and have the base class pass the state into the DoWork method.
public class MyState //TODO give better name
{
public int State1 { get; set; }
public int State2 { get; set; }
}
public class ABase
{
public MyState state = new MyState()
{
State1 = 1,
State2 = 2
};
List<Action<MyState>> workers = new List<Action<MyState>>();
public ABase()
{
CreateWorkers();
}
public void DoWork()
{
foreach (var action in workers)
{
action(state);
}
}
private void CreateWorkers()
{
workers.Add(new Worker1().DoWork);
workers.Add(Worker2.Process);
}
}
public class Worker1
{
public void DoWork(MyState state)
{
Console.WriteLine(state.State1);
}
}
public class Worker2
{
public static void Process(MyState state)
{
Console.WriteLine(state.State2);
}
}

Categories

Resources