Swift,遗传算法中的协议和泛型

Swift, Protocols and Generics in Genetic Algorithm

我正在尝试从 Java 切换到 Swift 并提高我的编程技能。

但是,在研究了

之后,我在理解泛型在Swift中的工作方式时遇到了一些困难:

https://docs.swift.org/swift-book/LanguageGuide/Generics.html

我已经开始通过编写一些协议来编写遗传算法了。

protocol Point : Equatable {
    var identifier: String { get }
    var x: Double { get }
    var y: Double { get }
    func distance<P : Point>(to point: P) -> Double
}

protocol Individual {
    associatedtype P : Point
    var fitness: Double { get }
    var chromosomes: [P] { get }
}

现在我想创建一个符合 Individual 协议的结构。

编译的唯一尝试是

struct Route : Individual {
    typealias P = City;
    var fitness: Double { 0.0 }
    var chromosomes: [City]
}

但是,我想让 Route 尽可能通用,因此我不想说它使用 City 作为 Point 的实现。我希望 Route 知道它适用于符合 Point 协议的对象数组。

非常感谢你的帮助。

提前致谢。

首先,我建议在 distance(to:) 方法上添加一个 Self 要求。 Self 只是告诉编译器参数与符合类型是同一类型。

protocol Point : Equatable {
    var identifier: String { get }
    var x: Double { get }
    var y: Double { get }
    func distance(to point: Self) -> Double
}

因此,在您的 City 结构中 point 也必须是 City.

类型
struct City: Point {
    var identifier: String
    var x: Double
    var y: Double

    func distance(to point: City) -> Double {
        return .zero
    }
}

您可以通过添加通用参数使您的 Route 结构更加灵活,该通用参数也满足 Individual 协议强加的关联类型要求。

struct Route<P: Point>: Individual {
    var fitness: Double { 0.0 }
    var chromosomes: [P]
}

实例化一个Route:

var cityRoute = Route<City>(chromosomes: [])

您可以创建一个实现特定协议的 class 数组,因此例如在这种情况下您将拥有:

 struct Route: Individual {
    typealias P = City;
    var fitness: Double { 0.0 }
    var chromosomes: [Point]
}

并且您可以调用所有协议方法。