Replies: 8 comments 5 replies
-
小4 ( 程式 ) 答案public class Question1
{
public interface IState
{
public int EnterAP { get; }
bool CanEnter(FiniteStateMachine fsm);
void OnEnter(FiniteStateMachine fsm);
void OnExit(FiniteStateMachine fsm);
}
public class FiniteStateMachine
{
public Bot Target { get; }
public IState CurrentState { get; private set; }
public FiniteStateMachine(Bot target)
{
if (target == null)
throw new ArgumentNullException("target is null");
Target = target;
}
public void SetState(IState state)
{
if (state == null)
{
throw new ArgumentNullException();
}
if (!state.CanEnter(this))
{
return;
}
if (CurrentState != null)
{
CurrentState.OnExit(this);
}
state.OnEnter(this);
CurrentState = state;
}
}
public class Bot
{
public int ActionPoint { get; private set; }
private List<string> _records = new List<string>();
public Bot(int actionPoint)
{
ActionPoint = actionPoint;
}
public void AddRecord(string record)
{
_records.Add(record);
}
public string[] GetRecords()
{
return _records.ToArray();
}
public void ConsumeAP(int ap)
{
if (ap < 0)
throw new ArgumentOutOfRangeException("consumed ap must be greater than zero");
ActionPoint -= ap;
}
public void RecoveryAP(int ap)
{
if (ap < 0)
throw new ArgumentOutOfRangeException("added ap must be greater than zero");
ActionPoint += ap;
}
}
public class IdleState : IState
{
public int EnterAP => 2;
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException();
}
return true;
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException();
}
fsm.Target.AddRecord("Enter (Idle)");
fsm.Target.RecoveryAP(EnterAP);
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException();
}
fsm.Target.AddRecord("Exit (Idle)");
}
}
public class WalkState : IState
{
public int EnterAP => -1;
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException();
}
return fsm.Target.ActionPoint >= (int)MathF.Abs(EnterAP);
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException();
}
fsm.Target.AddRecord("Enter (Walk)");
fsm.Target.ConsumeAP((int)MathF.Abs(EnterAP));
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException();
}
fsm.Target.AddRecord("Exit (Walk)");
}
}
public class AttackState : IState
{
public int EnterAP => -2;
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException();
}
return fsm.Target.ActionPoint >= (int)MathF.Abs(EnterAP);
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException();
}
fsm.Target.AddRecord("Enter (Attack)");
fsm.Target.ConsumeAP((int)MathF.Abs(EnterAP));
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException();
}
fsm.Target.AddRecord("Exit (Attack)");
}
}
public class JumpState : IState
{
public int EnterAP => -1;
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException();
}
return fsm.Target.ActionPoint >= (int)MathF.Abs(EnterAP);
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException();
}
fsm.Target.AddRecord("Enter (Jump)");
fsm.Target.ConsumeAP((int)MathF.Abs(EnterAP));
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException();
}
fsm.Target.AddRecord("Exit (Jump)");
}
}
} 反饋不太敢再Question1裡面修改新增東西 感覺加了以後就是鴿子直升機 動是可以動 但不是老師要的效果 |
Beta Was this translation helpful? Give feedback.
-
JIA(程式新手) 我的答案public class IdleState : BaseState
{
protected override int _addActionPoint => 2;
protected override int _reduceActionPoint => 0;
protected override string _state => "Idle";
}
public class WalkState : BaseState
{
protected override int _addActionPoint => 0;
protected override int _reduceActionPoint => 1;
protected override string _state => "Walk";
}
public class JumpState : BaseState
{
protected override int _addActionPoint => 0;
protected override int _reduceActionPoint => 1;
protected override string _state => "Jump";
}
public class AttackState : BaseState
{
protected override int _addActionPoint => 0;
protected override int _reduceActionPoint => 2;
protected override string _state => "Attack";
}
public abstract class BaseState : IState
{
protected abstract int _reduceActionPoint { get; }
protected abstract int _addActionPoint { get; }
protected abstract string _state { get; }
public virtual bool CanEnter(FiniteStateMachine fsm)
{
var bot = GetTarget<Bot>(fsm);
return (bot.ActionPoint - _reduceActionPoint) >= 0;
}
public virtual void OnEnter(FiniteStateMachine fsm)
{
var bot = GetTarget<Bot>(fsm);
if (_addActionPoint > 0) bot.RecoveryAP(_addActionPoint);
if (_reduceActionPoint > 0) bot.ConsumeAP(_reduceActionPoint);
bot.AddRecord($"Enter ({_state})");
}
public virtual void OnExit(FiniteStateMachine fsm)
{
var bot = GetTarget<Bot>(fsm);
bot.AddRecord($"Exit ({_state})");
}
public T GetTarget<T>(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException("Fsm is null.");
if (!(fsm.Target is T))
throw new InvalidCastException($"Unable to cast 'fsm.Target' to {nameof(T)} type.");
return (T)fsm.Target;
}
}
public interface IState
{
bool CanEnter(FiniteStateMachine fsm);
void OnEnter(FiniteStateMachine fsm);
void OnExit(FiniteStateMachine fsm);
}
public class FiniteStateMachine
{
public object Target { get; }
public IState CurrentState { get; private set; }
public FiniteStateMachine(object target)
{
if (target == null)
throw new ArgumentNullException("target is null");
Target = target;
}
public void SetState(IState state)
{
if (state == null)
throw new ArgumentNullException("state is null");
if (!state.CanEnter(this))
return;
if (CurrentState != null)
CurrentState.OnExit(this);
CurrentState = state;
CurrentState.OnEnter(this);
}
}
public class Bot
{
private int _actionPoint;
public int ActionPoint { get => _actionPoint; }
private List<string> _records = new List<string>();
public Bot(int actionPoint)
{
_actionPoint = actionPoint;
}
public void AddRecord(string record)
{
_records.Add(record);
}
public string[] GetRecords()
{
return _records.ToArray();
}
public void ConsumeAP(int ap)
{
if (ap < 0)
throw new ArgumentOutOfRangeException("consumed ap must be greater than zero");
_actionPoint -= ap;
}
public void RecoveryAP(int ap)
{
if (ap < 0)
throw new ArgumentOutOfRangeException("added ap must be greater than zero");
_actionPoint += ap;
}
} |
Beta Was this translation helpful? Give feedback.
-
老蕭OLDShaw(程式) 我的答案public class Question1
{
/// <summary>
/// A state for finite state machine
/// </summary>
public interface IState
{
/// <summary>
/// Check if the state can be entered
/// </summary>
/// <returns>enterable</returns>
bool CanEnter(FiniteStateMachine fsm);
/// <summary>
/// Enter the state
/// </summary>
void OnEnter(FiniteStateMachine fsm);
/// <summary>
/// Exit the state
/// </summary>
/// <param name="fsm"></param>
void OnExit(FiniteStateMachine fsm);
}
/// <summary>
/// Finite state machine
/// </summary>
public class FiniteStateMachine
{
/// <summary>
/// The target of model
/// </summary>
public object Target { get; }
/// <summary>
/// The current state of machine
/// </summary>
public IState CurrentState { get; private set; }
#region -- Constructor --
public FiniteStateMachine(object target)
{
if (target == null)
throw new ArgumentNullException("target is null");
Target = target;
}
#endregion
/// <summary>
/// Exit current state and enter next state
/// </summary>
/// <exception cref="ArgumentNullException">if the specific state is null</exception>
public void SetState(IState state)
{
if(state == null)
throw new ArgumentNullException("the specific state is null");
if (!state.CanEnter(this))
return;
if(CurrentState != null)
CurrentState.OnExit(this);
CurrentState = state;
CurrentState.OnEnter(this);
}
}
/// <summary>
/// The bot
/// </summary>
public class Bot
{
/// <summary>
/// Action Point for bot activity consuming
/// </summary>
public int ActionPoint { get; set; }
/// <summary>
/// The records of bot activities
/// </summary>
private List<string> _records = new List<string>();
#region -- Constructor --
public Bot(int actionPoint)
{
ActionPoint = actionPoint;
}
#endregion
/// <summary>
/// Add record into bot
/// </summary>
public void AddRecord(string record)
{
_records.Add(record);
}
/// <summary>
/// Get records of bot activities
/// </summary>
/// <returns></returns>
public string[] GetRecords()
{
return _records.ToArray();
}
/// <summary>
/// Consume ap for activity
/// </summary>
/// <exception cref="ArgumentOutOfRangeException">ap must be greater than zero</exception>
public void ConsumeAP(int ap)
{
if (ap < 0)
throw new ArgumentOutOfRangeException("consumed ap must be greater than zero");
ActionPoint -= ap;
}
/// <summary>
/// Recovery ap
/// </summary>
/// <exception cref="ArgumentOutOfRangeException">ap must be greater than zero</exception>
public void RecoveryAP(int ap)
{
if (ap < 0)
throw new ArgumentOutOfRangeException("added ap must be greater than zero");
ActionPoint += ap;
}
}
public abstract class WilyBotState : IState
{
protected abstract int _apChangeAmount { get; }
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException();
Bot bot = (Bot)fsm.Target;
if(_apChangeAmount < 0)
if (bot.ActionPoint < -_apChangeAmount) return false;
return true;
}
public virtual void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException();
Bot bot = (Bot)fsm.Target;
if(_apChangeAmount < 0)
bot.ConsumeAP(-_apChangeAmount);
else
bot.RecoveryAP(_apChangeAmount);
}
public virtual void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException();
}
}
public class IdleState : WilyBotState
{
protected override int _apChangeAmount => 2;
public override void OnEnter(FiniteStateMachine fsm)
{
base.OnEnter(fsm);
Bot bot = (Bot)fsm.Target;
bot.AddRecord($"Enter (Idle)");
}
public override void OnExit(FiniteStateMachine fsm)
{
base.OnExit(fsm);
Bot bot = (Bot)fsm.Target;
bot.AddRecord($"Exit (Idle)");
}
}
public class WalkState : WilyBotState
{
protected override int _apChangeAmount => -1;
public override void OnEnter(FiniteStateMachine fsm)
{
base.OnEnter(fsm);
Bot bot = (Bot)fsm.Target;
bot.AddRecord($"Enter (Walk)");
}
public override void OnExit(FiniteStateMachine fsm)
{
base.OnExit(fsm);
Bot bot = (Bot)fsm.Target;
bot.AddRecord($"Exit (Walk)");
}
}
public class JumpState : WilyBotState
{
protected override int _apChangeAmount => -1;
public override void OnEnter(FiniteStateMachine fsm)
{
base.OnEnter(fsm);
Bot bot = (Bot)fsm.Target;
bot.AddRecord($"Enter (Jump)");
}
public override void OnExit(FiniteStateMachine fsm)
{
base.OnExit(fsm);
Bot bot = (Bot)fsm.Target;
bot.AddRecord($"Exit (Jump)");
}
}
public class AttackState : WilyBotState
{
protected override int _apChangeAmount => -2;
public override void OnEnter(FiniteStateMachine fsm)
{
base.OnEnter(fsm);
Bot bot = (Bot)fsm.Target;
bot.AddRecord($"Enter (Attack)");
}
public override void OnExit(FiniteStateMachine fsm)
{
base.OnExit(fsm);
Bot bot = (Bot)fsm.Target;
bot.AddRecord($"Exit (Attack)");
}
}
} 專案原本是用Github Desktop抓的,但不知道為甚麼,這次Pull不下來,說什麼"There are unresolved conflicts in the working directory.",但明明所有衝突都解決了啊 ==? |
Beta Was this translation helpful? Give feedback.
-
Cliff Lee CL (程式、專案管理) 我的答案 public class Question1
{
/// <summary>
/// A state for finite state machine
/// </summary>
public interface IState
{
int ActionPointDiff { get; }
/// <summary>
/// Check if the state can be entered
/// </summary>
/// <returns>enterable</returns>
bool CanEnter(FiniteStateMachine fsm);
/// <summary>
/// Enter the state
/// </summary>
void OnEnter(FiniteStateMachine fsm);
/// <summary>
/// Exit the state
/// </summary>
/// <param name="fsm"></param>
void OnExit(FiniteStateMachine fsm);
}
public class IdleState : IState
{
public int ActionPointDiff => 2;
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm is null)
throw new ArgumentNullException("fsm is null");
if (fsm.Target is not Bot bot)
throw new ArgumentNullException("bot is null");
return true;
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm is null)
throw new ArgumentNullException("fsm is null");
if (fsm.Target is not Bot bot)
throw new ArgumentNullException("bot is null");
bot.AddRecord("Enter (Idle)");
bot.RecoveryAP(ActionPointDiff);
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm is null)
throw new ArgumentNullException("fsm is null");
if (fsm.Target is not Bot bot)
throw new ArgumentNullException("bot is null");
bot.AddRecord("Exit (Idle)");
}
}
public class WalkState : IState
{
public int ActionPointDiff => 1;
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm is null)
throw new ArgumentNullException("fsm is null");
if (fsm.Target is not Bot bot)
throw new ArgumentNullException("bot is null");
return bot.ActionPoint >= ActionPointDiff;
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm is null)
throw new ArgumentNullException("fsm is null");
if (fsm.Target is not Bot bot)
throw new ArgumentNullException("bot is null");
bot.AddRecord("Enter (Walk)");
bot.ConsumeAP(ActionPointDiff);
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm is null)
throw new ArgumentNullException("fsm is null");
if (fsm.Target is not Bot bot)
throw new ArgumentNullException("bot is null");
bot.AddRecord("Exit (Walk)");
}
}
public class JumpState : IState
{
public int ActionPointDiff => 1;
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm is null)
throw new ArgumentNullException("fsm is null");
if (fsm.Target is not Bot bot)
throw new ArgumentNullException("bot is null");
return bot.ActionPoint >= ActionPointDiff;
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm is null)
throw new ArgumentNullException("fsm is null");
if (fsm.Target is not Bot bot)
throw new ArgumentNullException("bot is null");
bot.AddRecord("Enter (Jump)");
bot.ConsumeAP(ActionPointDiff);
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm is null)
throw new ArgumentNullException("fsm is null");
if (fsm.Target is not Bot bot)
throw new ArgumentNullException("bot is null");
bot.AddRecord("Exit (Jump)");
}
}
public class AttackState : IState
{
public int ActionPointDiff => 2;
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm is null)
throw new ArgumentNullException("fsm is null");
if (fsm.Target is not Bot bot)
throw new ArgumentNullException("bot is null");
return bot.ActionPoint >= ActionPointDiff;
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm is null)
throw new ArgumentNullException("fsm is null");
if (fsm.Target is not Bot bot)
throw new ArgumentNullException("bot is null");
bot.AddRecord("Enter (Attack)");
bot.ConsumeAP(ActionPointDiff);
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm is null)
throw new ArgumentNullException("fsm is null");
if (fsm.Target is not Bot bot)
throw new ArgumentNullException("bot is null");
bot.AddRecord("Exit (Attack)");
}
}
/// <summary>
/// Finite state machine
/// </summary>
public class FiniteStateMachine
{
/// <summary>
/// The target of model
/// </summary>
public object Target { get; }
/// <summary>
/// The current state of machine
/// </summary>
public IState CurrentState { get; private set; }
#region -- Constructor --
public FiniteStateMachine(object target)
{
if (target == null)
throw new ArgumentNullException("target is null");
Target = target;
}
#endregion
/// <summary>
/// Exit current state and enter next state
/// </summary>
/// <exception cref="ArgumentNullException">if the specific state is null</exception>
public void SetState(IState state)
{
if (state is null)
throw new ArgumentNullException("state is null");
if (!state.CanEnter(this))
return;
CurrentState?.OnExit(this);
CurrentState = state;
CurrentState.OnEnter(this);
}
}
/// <summary>
/// The bot
/// </summary>
public class Bot
{
/// <summary>
/// Action Point for bot activity consuming
/// </summary>
public int ActionPoint => actionPoint;
private int actionPoint;
/// <summary>
/// The records of bot activities
/// </summary>
private List<string> _records = new List<string>();
#region -- Constructor --
public Bot(int actionPoint)
{
this.actionPoint = actionPoint;
}
#endregion
/// <summary>
/// Add record into bot
/// </summary>
public void AddRecord(string record)
{
_records.Add(record);
}
/// <summary>
/// Get records of bot activities
/// </summary>
/// <returns></returns>
public string[] GetRecords()
{
return _records.ToArray();
}
/// <summary>
/// Consume ap for activity
/// </summary>
/// <exception cref="ArgumentOutOfRangeException">ap must be greater than zero</exception>
public void ConsumeAP(int ap)
{
if (ap < 0)
throw new ArgumentOutOfRangeException("consumed ap must be greater than zero");
actionPoint -= ap;
}
/// <summary>
/// Recovery ap
/// </summary>
/// <exception cref="ArgumentOutOfRangeException">ap must be greater than zero</exception>
public void RecoveryAP(int ap)
{
if (ap < 0)
throw new ArgumentOutOfRangeException("added ap must be greater than zero");
actionPoint += ap;
}
}
} |
Beta Was this translation helpful? Give feedback.
-
小鲨 (程式) 答案public class Question1
{
/// <summary>
/// A state for finite state machine
/// </summary>
public interface IState
{
/// <summary>
/// Check if the state can be entered
/// </summary>
/// <returns>enterable</returns>
bool CanEnter(FiniteStateMachine fsm);
/// <summary>
/// Enter the state
/// </summary>
void OnEnter(FiniteStateMachine fsm);
/// <summary>
/// Exit the state
/// </summary>
/// <param name="fsm"></param>
void OnExit(FiniteStateMachine fsm);
}
/// <summary>
/// An idle state
/// </summary>
public class IdleState : IState
{
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException("fsm is null");
return true;
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException("fsm is null");
((Bot)(fsm.Target)).RecoveryAP(2);
((Bot)(fsm.Target)).AddRecord("Enter (Idle)");
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException("fsm is null");
((Bot)(fsm.Target)).AddRecord("Exit (Idle)");
}
}
/// <summary>
/// A walk state
/// </summary>
public class WalkState : IState
{
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException("fsm is null");
if(((Bot)(fsm.Target)).ActionPoint >= 1)
return true;
else
return false;
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException("fsm is null");
((Bot)(fsm.Target)).ConsumeAP(1);
((Bot)(fsm.Target)).AddRecord("Enter (Walk)");
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException("fsm is null");
((Bot)(fsm.Target)).AddRecord("Exit (Walk)");
}
}
/// <summary>
/// An attack state
/// </summary>
public class AttackState : IState
{
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException("fsm is null");
if(((Bot)(fsm.Target)).ActionPoint >= 2)
return true;
else
return false;
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException("fsm is null");
((Bot)(fsm.Target)).ConsumeAP(2);
((Bot)(fsm.Target)).AddRecord("Enter (Attack)");
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException("fsm is null");
((Bot)(fsm.Target)).AddRecord("Exit (Attack)");
}
}
/// <summary>
/// A jump state
/// </summary>
public class JumpState : IState
{
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException("fsm is null");
if(((Bot)(fsm.Target)).ActionPoint >= 1)
return true;
else
return false;
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException("fsm is null");
((Bot)(fsm.Target)).ConsumeAP(1);
((Bot)(fsm.Target)).AddRecord("Enter (Jump)");
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException("fsm is null");
((Bot)(fsm.Target)).AddRecord("Exit (Jump)");
}
}
/// <summary>
/// Finite state machine
/// </summary>
public class FiniteStateMachine
{
/// <summary>
/// The target of model
/// </summary>
public object Target { get; }
/// <summary>
/// The current state of machine
/// </summary>
public IState CurrentState { get; private set; }
#region -- Constructor --
public FiniteStateMachine(object target)
{
if (target == null)
throw new ArgumentNullException("target is null");
Target = target;
}
#endregion
/// <summary>
/// Exit current state and enter next state
/// </summary>
/// <exception cref="ArgumentNullException">if the specific state is null</exception>
public void SetState(IState state)
{
if (state == null)
throw new ArgumentNullException("state is null");
if (state.CanEnter(this))
{
if (CurrentState != null)
CurrentState.OnExit(this);
CurrentState = state;
CurrentState.OnEnter(this);
}
}
}
/// <summary>
/// The bot
/// </summary>
public class Bot
{
/// <summary>
/// Action Point for bot activity consuming
/// </summary>
public int ActionPoint => _actionPoint;
private int _actionPoint;
/// <summary>
/// The records of bot activities
/// </summary>
private List<string> _records = new List<string>();
#region -- Constructor --
public Bot(int actionPoint)
{
_actionPoint = actionPoint;
}
#endregion
/// <summary>
/// Add record into bot
/// </summary>
public void AddRecord(string record)
{
_records.Add(record);
}
/// <summary>
/// Get records of bot activities
/// </summary>
/// <returns></returns>
public string[] GetRecords()
{
return _records.ToArray();
}
/// <summary>
/// Consume ap for activity
/// </summary>
/// <exception cref="ArgumentOutOfRangeException">ap must be greater than zero</exception>
public void ConsumeAP(int ap)
{
if (ap < 0)
throw new ArgumentOutOfRangeException("consumed ap must be greater than zero");
_actionPoint -= ap;
}
/// <summary>
/// Recovery ap
/// </summary>
/// <exception cref="ArgumentOutOfRangeException">ap must be greater than zero</exception>
public void RecoveryAP(int ap)
{
if (ap < 0)
throw new ArgumentOutOfRangeException("added ap must be greater than zero");
_actionPoint += ap;
}
}
} |
Beta Was this translation helpful? Give feedback.
-
肉鬆(程式 / 音樂) 我的答案 public class Question1
{
public interface IState
{
bool CanEnter(FiniteStateMachine fsm);
void OnEnter(FiniteStateMachine fsm);
void OnExit(FiniteStateMachine fsm);
public int EnterAP { get; }
public string stateName { get; }
}
public class FiniteStateMachine
{
public Bot Target { get; }
public IState CurrentState { get; private set; }
public FiniteStateMachine(Bot target)
{
if (target == null)
throw new ArgumentNullException("target is null");
Target = target;
}
public void SetState(IState state)
{
if (state == null)
{
throw new ArgumentNullException("state is null");
}
else if (state.CanEnter(this)==false)
{
return;
}
else if (CurrentState != null)
{
CurrentState.OnExit(this);
}
state.OnEnter(this);
CurrentState = state;
}
}
public class Bot
{
public int ActionPoint { get; private set; }
private List<string> _records = new List<string>();
public Bot(int actionPoint)
{
ActionPoint = actionPoint;
}
public void AddRecord(string record)
{
_records.Add(record);
}
public string[] GetRecords()
{
return _records.ToArray();
}
public void ConsumeAP(int ap)
{
if (ap < 0)
throw new ArgumentOutOfRangeException("行動點耗盡!");
else
ActionPoint -= ap;
}
public void RecoveryAP(int ap)
{
if (ap < 0)
throw new ArgumentOutOfRangeException("行動點耗盡!");
else
ActionPoint += ap;
}
}
public class IdleState : IState
{
public int EnterAP => 2;
public string stateName => "Idle";
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("fsm is null");
}
return true;
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("fsm is null");
}
fsm.Target.AddRecord(string.Format("Enter ({0})",stateName));
fsm.Target.RecoveryAP(EnterAP);
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("fsm is null");
}
fsm.Target.AddRecord(string.Format("Exit ({0})", stateName));
}
}
public class WalkState : IState
{
public int EnterAP => -1;
public string stateName => "Walk";
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("fsm is null");
}
return fsm.Target.ActionPoint >= (int)MathF.Abs(EnterAP);
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("fsm is null");
}
fsm.Target.AddRecord(string.Format("Enter ({0})", stateName));
fsm.Target.ConsumeAP((int)MathF.Abs(EnterAP));
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("fsm is null");
}
fsm.Target.AddRecord(string.Format("Exit ({0})", stateName));
}
}
public class AttackState : IState
{
public int EnterAP => -2;
public string stateName => "Attack";
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("fsm is null");
}
return fsm.Target.ActionPoint >= (int)MathF.Abs(EnterAP);
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("fsm is null");
}
fsm.Target.AddRecord(string.Format("Enter ({0})", stateName));
fsm.Target.ConsumeAP((int)MathF.Abs(EnterAP));
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("fsm is null");
}
fsm.Target.AddRecord(string.Format("Exit ({0})", stateName));
}
}
public class JumpState : IState
{
public int EnterAP => -1;
public string stateName => "Jump";
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("fsm is null");
}
return fsm.Target.ActionPoint >= (int)MathF.Abs(EnterAP);
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("fsm is null");
}
fsm.Target.AddRecord(string.Format("Enter ({0})", stateName));
fsm.Target.ConsumeAP((int)MathF.Abs(EnterAP));
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("fsm is null");
}
fsm.Target.AddRecord(string.Format("Exit ({0})", stateName));
}
}
} 課程回饋消化速度越來越慢了qwq |
Beta Was this translation helpful? Give feedback.
-
Snoweve (程式) 我的答案using System;
using System.Collections.Generic;
namespace PG0006.Questions
{
public class Question1
{
/// <summary>
/// A state for finite state machine
/// </summary>
public interface IState
{
/// <summary>
/// Check if the state can be entered
/// </summary>
/// <returns>enterable</returns>
bool CanEnter(FiniteStateMachine fsm);
/// <summary>
/// Enter the state
/// </summary>
void OnEnter(FiniteStateMachine fsm);
/// <summary>
/// Exit the state
/// </summary>
/// <param name="fsm"></param>
void OnExit(FiniteStateMachine fsm);
}
/// <summary>
/// Finite state machine
/// </summary>
public class FiniteStateMachine
{
/// <summary>
/// The target of model
/// </summary>
public object Target { get; }
/// <summary>
/// The current state of machine
/// </summary>
public IState CurrentState { get; private set; }
#region -- Constructor --
public FiniteStateMachine(object target)
{
if (target == null)
throw new ArgumentNullException("target is null");
Target = target;
}
#endregion
/// <summary>
/// Exit current state and enter next state
/// </summary>
/// <exception cref="ArgumentNullException">if the specific state is null</exception>
public void SetState(IState state)
{
if (state == null)
{
throw new ArgumentNullException("state");
}
if (!state.CanEnter(this))
{
return;
}
if (CurrentState != null)
{
CurrentState.OnExit(this);
}
CurrentState = state;
CurrentState.OnEnter(this);
}
}
/// <summary>
/// The bot
/// </summary>
public class Bot
{
/// <summary>
/// Action Point for bot activity consuming
/// </summary>
private int _actionPoint;
public int ActionPoint => _actionPoint;
/// <summary>
/// The records of bot activities
/// </summary>
private List<string> _records = new List<string>();
#region -- Constructor --
public Bot(int actionPoint)
{
_actionPoint = actionPoint;
}
#endregion
/// <summary>
/// Add record into bot
/// </summary>
public void AddRecord(string record)
{
_records.Add(record);
}
/// <summary>
/// Get records of bot activities
/// </summary>
/// <returns></returns>
public string[] GetRecords()
{
return _records.ToArray();
}
/// <summary>
/// Consume ap for activity
/// </summary>
/// <exception cref="ArgumentOutOfRangeException">ap must be greater than zero</exception>
public void ConsumeAP(int ap)
{
if (ap < 0)
throw new ArgumentOutOfRangeException("consumed ap must be greater than zero");
_actionPoint -= ap;
}
/// <summary>
/// Recovery ap
/// </summary>
/// <exception cref="ArgumentOutOfRangeException">ap must be greater than zero</exception>
public void RecoveryAP(int ap)
{
if (ap < 0)
throw new ArgumentOutOfRangeException("added ap must be greater than zero");
_actionPoint += ap;
}
}
public abstract class BotState : IState
{
protected abstract int AP { get; }
protected abstract string StateName { get; }
public virtual bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("fsm is null");
}
Bot bot = GetBot(fsm.Target);
return bot.ActionPoint >= AP;
}
public virtual void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("fsm is null");
}
Bot bot = GetBot(fsm.Target);
bot.ConsumeAP(AP);
bot.AddRecord(string.Format("Enter ({0})", StateName));
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("fsm is null");
}
Bot bot = GetBot(fsm.Target);
bot.AddRecord(string.Format("Exit ({0})", StateName));
}
protected Bot GetBot(object target)
{
if(target == null)
{
throw new ArgumentNullException("沒有指定目標");
}
Bot bot = target as Bot;
return bot;
}
}
public class IdleState : BotState
{
protected override int AP => 2;
protected override string StateName => "Idle";
public override bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException("fsm is null");
return true;
}
public override void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
throw new ArgumentNullException("fsm is null");
var bot = GetBot(fsm.Target);
bot.RecoveryAP(AP);
bot.AddRecord(string.Format("Enter ({0})", StateName));
}
}
public class WalkState : BotState
{
protected override int AP => 1;
protected override string StateName => "Walk";
}
public class JumpState : BotState
{
protected override int AP => 1;
protected override string StateName => "Jump";
}
public class AttackState : BotState
{
protected override int AP => 2;
protected override string StateName =>"Attack";
}
}
} 課程回饋
這次作業對我來說很難吸收,這次是邊看著答案邊思考,可是寫完有確定學進去蠻開心的
|
Beta Was this translation helpful? Give feedback.
-
補課程 肥羊(程式) 我的答案namespace PG0006.Questions
{
public class Question1
{
/// <summary>
/// A state for finite state machine
/// </summary>
public interface IState
{
/// <summary>
/// Check if the state can be entered
/// </summary>
/// <returns>enterable</returns>
bool CanEnter(FiniteStateMachine fsm);
/// <summary>
/// Enter the state
/// </summary>
void OnEnter(FiniteStateMachine fsm);
/// <summary>
/// Exit the state
/// </summary>
/// <param name="fsm"></param>
void OnExit(FiniteStateMachine fsm);
}
/// <summary>
/// Finite state machine
/// </summary>
public class FiniteStateMachine
{
/// <summary>
/// The target of model
/// </summary>
public Object Target { get; }
/// <summary>
/// The current state of machine
/// </summary>
public IState CurrentState { get; private set; }
#region -- Constructor --
public FiniteStateMachine(Object target)
{
if (target == null)
throw new ArgumentNullException("target is null");
Target = target;
}
#endregion
/// <summary>
/// Exit current state and enter next state
/// </summary>
/// <exception cref="ArgumentNullException">if the specific state is null</exception>
public void SetState(IState state)
{
if (state == null)
{
throw new ArgumentNullException("state is null");
}
else if (!state.CanEnter(this))//沒進入就跳出
{
return;
}
else if (CurrentState != null)
{
CurrentState.OnExit(this);//離開現在state
}
CurrentState = state;//刷新現在state
CurrentState.OnEnter(this);//進入state
}
}
/// <summary>
/// The bot
/// </summary>
public class Bot
{
/// <summary>
/// Action Point for bot activity consuming
/// </summary>
public int ActionPoint { get; set; }
/// <summary>
/// The records of bot activities
/// </summary>
private List<string> _records = new List<string>();
#region -- Constructor --
public Bot(int actionPoint)
{
ActionPoint = actionPoint;
}
#endregion
/// <summary>
/// Add record into bot
/// </summary>
public void AddRecord(string record)
{
_records.Add(record);
}
/// <summary>
/// Get records of bot activities
/// </summary>
/// <returns></returns>
public string[] GetRecords()
{
return _records.ToArray();
}
/// <summary>
/// Consume ap for activity
/// </summary>
/// <exception cref="ArgumentOutOfRangeException">ap must be greater than zero</exception>
public void ConsumeAP(int ap)
{
if (ap < 0)
throw new ArgumentOutOfRangeException("消耗行動點為負數!");
else
ActionPoint -= ap;
}
/// <summary>
/// Recovery ap
/// </summary>
/// <exception cref="ArgumentOutOfRangeException">ap must be greater than zero</exception>
public void RecoveryAP(int ap)
{
if (ap < 0)
throw new ArgumentOutOfRangeException("增加行動點為負數!");
else
ActionPoint += ap;
}
}
public class IdleState : IState
{
private int EnterAP => 2;
private string StateName => "(Idle)";
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("Fsm is Null");
}
return true;
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("Fsm is Null");
}
Bot bot = (Bot)fsm.Target;
bot.RecoveryAP(EnterAP);
bot.AddRecord($"Enter {StateName}");
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("Fsm is Null");
}
Bot bot = (Bot)fsm.Target;
bot.AddRecord($"Exit {StateName}");
}
}
public class WalkState : IState
{
private int EnterAP => -1;
private string StateName => "(Walk)";
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("Fsm is Null");
}
if (((Bot)(fsm.Target)).ActionPoint >= 1)
return true;
else
return false;
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("Fsm is Null");
}
Bot bot = (Bot)fsm.Target;
bot.ConsumeAP((int)MathF.Abs(EnterAP));
bot.AddRecord($"Enter {StateName}");
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("Fsm is Null");
}
Bot bot = (Bot)fsm.Target;
bot.AddRecord($"Exit {StateName}");
}
}
public class JumpState : IState
{
private int EnterAP => -1;
private string StateName => "(Jump)";
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("Fsm is Null");
}
if (((Bot)(fsm.Target)).ActionPoint >= 1)
return true;
else
return false;
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("Fsm is Null");
}
Bot bot = (Bot)fsm.Target;
bot.ConsumeAP((int)MathF.Abs(EnterAP));
bot.AddRecord($"Enter {StateName}");
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("Fsm is Null");
}
Bot bot = (Bot)fsm.Target;
bot.AddRecord($"Exit {StateName}");
}
}
public class AttackState : IState
{
private int EnterAP => -2;
private string StateName => "(Attack)";
public bool CanEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("Fsm is Null");
}
if (((Bot)(fsm.Target)).ActionPoint >= 2)
return true;
else
return false;
}
public void OnEnter(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("Fsm is Null");
}
Bot bot = (Bot)fsm.Target;
bot.ConsumeAP((int)MathF.Abs(EnterAP));
bot.AddRecord($"Enter {StateName}");
}
public void OnExit(FiniteStateMachine fsm)
{
if (fsm == null)
{
throw new ArgumentNullException("Fsm is Null");
}
Bot bot = (Bot)fsm.Target;
bot.AddRecord($"Exit {StateName}");
}
}
}
} |
Beta Was this translation helpful? Give feedback.
-
Introduction
Background
威利博士是一個富有理想的機器人博士,雖然每次都有一個藍色混蛋試圖阻撓他,威利仍鍥而不捨的努力,隨著機器人的動作越來越複雜,威利想利用狀態機整理機器人們的行為邏輯;請大家幫幫威利博士吧...
Conditions
閒置(Idle): AP + 2 (AP為零依然可以進入)
走(Walk): AP-1
跳(Jump): AP-1
攻擊(Attack): AP-2
Answer
解答
測試案例中的命名都是狀態+State字尾,如果想改測試的命名也可以。
是否先使用abstract class去實作IState並沒有硬性規定,題目要求只要滿足IState介面即可,
如同影片中所提及,抽象類別的應用只用於有復用的情況,但不是必需的。
Beta Was this translation helpful? Give feedback.
All reactions