2

我正在构建一个简单的状态引擎,我想要一个可以在其中移动的状态集合。

我想解决这个问题的方法是枚举可能的状态,这些状态也定义了表示该状态的相应类,这样如果我决定移动到那个状态,我就可以动态地构造状态。

在下面的代码中,我尝试构建一个运行良好的 State 对象的枚举。我卡住的地方是,我怎样才能访问这个枚举的值作为我可以从中调用静态构造函数方法的类型?在下面的代码中,我得到的错误是尝试使用枚举值调用 moveToState 并不代表 StartupStates 类型,它似乎...

所以问题真的是,为什么这不起作用,或者我有什么其他方式可以枚举类类型和/或类级别(静态)方法来调用构造函数?

public enum StartupStates<State> {
case Start(StartState)
case DownloadFiles(DownloadFilesState)
 }

 public protocol State {
   var stateEngine : StateEngine {get set}
 }

public class StateEngine
{
    var currentState : State?
    public func moveToState(newState : StartupStates<State>)
    {
    }
}

public class StartState : BaseState
{
    func doStateTasks()
    {
        // Move to next state, downloading files
        // ERROR IS HERE: 
        // "Cannot convert file of type '(DownloadFileState)->StartupStates<...>' to expected argument type 'StartupStates<State>'"

        stateEngine.moveToState(StartupStates.DownloadFiles)
    }
}

public class DownloadFilesState : BaseState
{
}


public class BaseState : State {
    public var stateEngine : StateEngine

    required public init( stateEngine : StateEngine ) {
        self.stateEngine = stateEngine
    }

    public static func stateCreator(stateEngine : StateEngine) -> Self {
        return self.init( stateEngine: stateEngine )
    }
}
4

3 回答 3

4

字符串解决方案:

NSClassFromString在这种情况下,您也许可以发挥自己的优势。考虑以下示例:

enum State: String {
    case StartState = "StartClass"
    case DownloadState = "DownloadClass"
    case BaseState = "BaseClass"

    var klass: AnyClass {
        return NSClassFromString(self.rawValue)!
    }
}

如果您正在寻找这种解决方案,请告诉我。

替代解决方案:

如果您不想依赖于键入字符串解决方案,那么您需要为类类型设置一个简单的 switch 语句:

class StartClass {}
class DownloadClass {}
class BaseClass {}

enum State {
    case StartState
    case DownloadState
    case BaseState

    var klass: AnyClass {
        switch self {
        case .StartState:
            return StartClass.self
        case .DownloadState:
            return DownloadClass.self
        case .BaseState:
            return BaseClass.self
        }
    }
}
于 2016-01-14T01:21:33.757 回答
0

这个怎么样:

class StartState : BaseState {
    func doStateTasks() {        
        let download = DownloadFilesState(stateEngine: StateEngine())
        stateEngine.moveToState(.DownloadFiles(download))
   }
}

因为DownloadFiles枚举需要一个DownloadFilesState在枚举中定义的对象。

于 2016-01-14T01:59:36.623 回答
0

使用完成处理程序而不是类类型怎么样?

protocol MyProtocol {}

class StartClass: MyProtocol {}
class DownloadClass: MyProtocol {}
class BaseClass: MyProtocol {}

enum State {
    case StartState
    case DownloadState
    case BaseState

    var completionHandler: () -> MyProtocol {
        switch self {
        case .StartState:
            return { return StartClass() }
        case .DownloadState:
            return { return DownloadClass() }
        case .BaseState:
            return { return BaseClass() }
        }
    }
}

从枚举值访问初始化的类。

var myState: State = .StartState
myState.completionHandler { initializedStartClass in
    InitializedStartClass.methods....
}
于 2021-03-23T15:43:41.403 回答