Menu
Coddy logo textTech

Comparable

Parte da seção Programação Orientada a Objetos do Journey de Swift da Coddy. Lição 39 de 57.

Comparable fornece a um tipo os operadores <, <=, > e >=. Você implementa apenas <; o Swift deriva o restante. Tipos Comparable podem ser ordenados com sorted() e usados com min() e max():

struct Version: Comparable {
    let major: Int, minor: Int

    static func < (lhs: Version, rhs: Version) -> Bool {
        (lhs.major, lhs.minor) < (rhs.major, rhs.minor)
    }
}

let versions = [Version(major: 2, minor: 1), Version(major: 1, minor: 9), Version(major: 2, minor: 0)]
let newest = versions.max()!
print("\(newest.major).\(newest.minor)")
print(versions.sorted().map { "\($0.major).\($0.minor)" })

Saída:

2.1
["1.9", "2.0", "2.1"]

Comparar tuplas compara suas partes na ordem, o que torna as comparações com várias chaves concisas. Aqui, as tarefas são ordenadas primeiro por prioridade e depois por nome:

struct Task: Comparable {
    let priority: Int
    let name: String

    static func < (lhs: Task, rhs: Task) -> Bool {
        (lhs.priority, lhs.name) < (rhs.priority, rhs.name)
    }
}

let tasks = [Task(priority: 2, name: "email"), Task(priority: 1, name: "fix"), Task(priority: 2, name: "call")]
print(tasks.sorted().map { $0.name })

Saída:

["fix", "call", "email"]

Enums sem valores associados podem estar em conformidade com Comparable sem escrever <: os casos são comparados na ordem em que são declarados:

enum Priority: Comparable {
    case low, medium, high
}

print(Priority.low < Priority.high)
print([Priority.high, .low, .medium].sorted())

Saída:

true
[main.Priority.low, main.Priority.medium, main.Priority.high]

sorted(by:) ordena com qualquer regra em uma chamada, enquanto Comparable define a ordem natural do tipo que sorted(), min() e max() usam em todo lugar:

struct Task: Comparable {
    let priority: Int
    let name: String
    static func < (lhs: Task, rhs: Task) -> Bool { lhs.priority < rhs.priority }
}

let tasks = [Task(priority: 3, name: "c"), Task(priority: 1, name: "a")]
print(tasks.sorted().map { $0.name })
print(tasks.sorted(by: >).map { $0.name })

Saída:

["a", "c"]
["c", "a"]
challenge icon

Desafio

Fácil

Faça Runner (nome e tempo de chegada como minutes, seconds) estar em conformidade com Comparable, de modo que um tempo mais rápido seja menor e tempos iguais sejam ordenados pelo nome. Complete podium(_:), que ordena os corredores com sorted() e retorna linhas no formato 1. Ada 20:05 para os três primeiros (menos se houver menos corredores), com os segundos preenchidos para dois dígitos.

O código fornecido lê linhas no formato name,mm:ss e imprime cada linha retornada.

Seu código deve estar em Runner.swift e Functions.swift. main.swift contém o código fornecido de entrada/saída e não pode ser editado.

Experimente você mesmo

// Código de entrada/saída fornecido: mantenha-o como está
var input: [String] = []
while let line = readLine() { input.append(line) }
let runners = input.map { line -> Runner in
    let p = line.split(separator: ",").map(String.init)
    let t = p[1].split(separator: ":").map { Int($0)! }
    return Runner(name: p[0], minutes: t[0], seconds: t[1])
}
for line in podium(runners) { print(line) }
quiz iconTeste seus conhecimentos

Esta lição inclui um quiz rápido. Comece a lição para respondê-lo e acompanhar seu progresso.

Todas as lições de Programação Orientada a Objetos

Pratique por conta própria: Playground de Swift