Swift Swith enum can';t继承方法,这是防止为每个枚举重写相同函数的最佳方法
因此,我正在使用路由器设计模式编写我的网络代码。我正在为我的应用程序的不同组件编写一个新的路由器(我应该这样做吗?我试图限制我的对象的代码行)。这是我的路由器号码。如果我使用的是一个类,我可以定义一次方法来填充HTTPMethod之类的变量,并在必要时重写它们。有没有一种方法可以通过枚举实现这一点?它是否值得实现,或者我是否应该重复相同的代码。除了httpMethod,还有一些其他地方,比如URL构造,我认为这可能会有所帮助。 我想我可以用协议做点什么,但不确定我是否在浪费时间Swift Swith enum can';t继承方法,这是防止为每个枚举重写相同函数的最佳方法,swift,Swift,因此,我正在使用路由器设计模式编写我的网络代码。我正在为我的应用程序的不同组件编写一个新的路由器(我应该这样做吗?我试图限制我的对象的代码行)。这是我的路由器号码。如果我使用的是一个类,我可以定义一次方法来填充HTTPMethod之类的变量,并在必要时重写它们。有没有一种方法可以通过枚举实现这一点?它是否值得实现,或者我是否应该重复相同的代码。除了httpMethod,还有一些其他地方,比如URL构造,我认为这可能会有所帮助。 我想我可以用协议做点什么,但不确定我是否在浪费时间 enum PRR
enum PRRouter: URLRequestConvertible {
static let baseURLString = "http://localhost:8000/"
case get(Int)
case create([String : Any])
case delete(Int)
func asURLRequest() throws -> URLRequest {
var method: HTTPMethod{
switch self {
case .get:
return .get
case .create:
return .post
case.delete:
return .delete
}
}
let params : ([String : Any]?) = {
switch self {
case .get, .delete:
return nil
case .create(let newTodo):
return newTodo
}
}()
let url : URL = {
let relativePath: String?
switch self{
case .get(let number):
relativePath = "test/\(number)"
case .create:
relativePath = "test/"
case .delete:
relativePath = "test/"
}
var url = URL(string: PRRouter.baseURLString)!
if let relativePath = relativePath {
url = url.appendingPathComponent(relativePath)
}
return url
}()
var urlRequest = URLRequest(url:url)
urlRequest.httpMethod = method.rawValue
let encoding = JSONEncoding.default
return try encoding.encode(urlRequest, with: params)
}
使枚举符合具有默认实现的协议
protocol P {
func f()
}
extension P {
func f() { print("default implementation") }
}
enum E: P {
case Foo
}
let e = E.Foo
e.f()
我在自己的项目中也做了类似的事情。下面是一个基于您的代码的示例,以帮助您入门:
protocol APIProtocol {
var path: String { get }
var method: HTTPMethods { get }
var bodyParameters: [String: Any?]? { get }
}
enum HTTPMethods: String {
case get = "GET"
case post = "POST"
}
enum PRRouter: APIProtocol {
case get(Int)
case create([String : Any])
case delete(Int)
var path: String {
switch self {
case let .get(number):
return "test/\(number)"
default:
return "test"
}
}
var method: HTTPMethods {
return .get
}
var bodyParameters: [String : Any?]? {
return nil
}
}
extension APIProtocol {
func execute(completion: @escaping ((Data?) -> Void)) -> URLSessionDataTask? {
guard let url = URL(string: "http://localhost:8000/\(path)") else { return nil }
var urlRequest = URLRequest(url: url)
urlRequest.httpMethod = method.rawValue
if let bodyParameters = bodyParameters {
urlRequest.httpBody = try? JSONSerialization.data(withJSONObject: bodyParameters, options: [.prettyPrinted])
}
let task = URLSession.shared.dataTask(with: urlRequest) { (data, urlResponse, error) in
completion(data)
}
task.resume()
return task
}
}
最后,您可以这样使用它:
let dataTask = PRRouter.get(2).execute { (data) in
//
}
您可以通过更改execute函数中的completion块以返回反序列化对象来进一步扩展此功能。谢谢,这正是我想要的!