简体   繁体   English

Swift:按字母顺序对对象数组进行排序

[英]Swift: Sort array of objects alphabetically

I have this:我有这个:

class Movies {
  Name:String
  Date:Int
}

and an array of [Movies].和一系列[电影]。 How do I sort the array alphabetically by name?如何按名称的字母顺序对数组进行排序? I've tried:我试过了:

movieArr = movieArr.sorted{ $0 < $1 }

and

movieArr = sorted(movieArr)

but that doesn't work because I'm not accessing the name attribute of Movies.但这不起作用,因为我没有访问 Movies 的 name 属性。

In the closure you pass to sort , compare the properties you want to sort by.在传递给sort的闭包中,比较要作为排序依据的属性。 Like this:像这样:

movieArr.sorted { $0.name < $1.name }

or the following in the cases that you want to bypass cases:或在您想要绕过案例的情况下执行以下操作:

movieArr.sorted { $0.name.lowercased() < $1.name.lowercased() }

Sidenote: Typically only types start with an uppercase letter;旁注:通常只有类型以大写字母开头; I'd recommend using name and date , not Name and Date .我建议使用namedate ,而不是NameDate


Example, in a playground:例如,在操场上:

class Movie {
    let name: String
    var date: Int?

    init(_ name: String) {
        self.name = name
    }
}

var movieA = Movie("A")
var movieB = Movie("B")
var movieC = Movie("C")

let movies = [movieB, movieC, movieA]
let sortedMovies = movies.sorted { $0.name < $1.name }
sortedMovies

sortedMovies will be in the order [movieA, movieB, movieC] sortedMovies将按顺序[movieA, movieB, movieC]

Swift5 Update Swift5 更新

channelsArray = channelsArray.sorted { (channel1, channel2) -> Bool in
            let channelName1 = channel1.name
            let channelName2 = channel2.name
            return (channelName1.localizedCaseInsensitiveCompare(channelName2) == .orderedAscending)

With Swift 3, you can choose one of the following ways to solve your problem.使用 Swift 3,您可以选择以下方法之一来解决您的问题。


1. Using sorted(by:​) with a Movie class that does not conform to Comparable protocol 1. 对不符合Comparable协议的Movie类使用sorted(by:​)

If your Movie class does not conform to Comparable protocol, you must specify in your closure the property on which you wish to use Array's sorted(by:​) method.如果你的Movie类不符合Comparable协议,你必须在你的闭包中指定你希望使用 Array 的sorted(by:​)方法的属性。

Movie class declaration: Movie类声明:

import Foundation

class Movie: CustomStringConvertible {

    let name: String
    var date: Date
    var description: String { return name }

    init(name: String, date: Date = Date()) {
        self.name = name
        self.date = date
    }

}

Usage:用法:

let avatarMovie = Movie(name: "Avatar")
let titanicMovie = Movie(name: "Titanic")
let piranhaMovie = Movie(name: "Piranha II: The Spawning")

let movies = [avatarMovie, titanicMovie, piranhaMovie]
let sortedMovies = movies.sorted(by: { $0.name < $1.name })
// let sortedMovies = movies.sorted { $0.name < $1.name } // also works

print(sortedMovies)

/*
prints: [Avatar, Piranha II: The Spawning, Titanic]
*/

2. Using sorted(by:​) with a Movie class that conforms to Comparable protocol 2. 将sorted(by:​)与符合Comparable协议的Movie类一起使用

However, by making your Movie class conform to Comparable protocol, you can have a much concise code when you want to use Array's sorted(by:​) method.但是,通过使您的Movie类符合Comparable协议,当您想要使用 Array 的sorted(by:​)方法时,您可以获得更简洁的代码。

Movie class declaration: Movie类声明:

import Foundation

class Movie: CustomStringConvertible, Comparable {

    let name: String
    var date: Date
    var description: String { return name }

    init(name: String, date: Date = Date()) {
        self.name = name
        self.date = date
    }

    static func ==(lhs: Movie, rhs: Movie) -> Bool {
        return lhs.name == rhs.name
    }

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

}

Usage:用法:

let avatarMovie = Movie(name: "Avatar")
let titanicMovie = Movie(name: "Titanic")
let piranhaMovie = Movie(name: "Piranha II: The Spawning")

let movies = [avatarMovie, titanicMovie, piranhaMovie]
let sortedMovies = movies.sorted(by: { $0 < $1 })
// let sortedMovies = movies.sorted { $0 < $1 } // also works
// let sortedMovies = movies.sorted(by: <) // also works

print(sortedMovies)

/*
 prints: [Avatar, Piranha II: The Spawning, Titanic]
 */

3. Using sorted() with a Movie class that conforms to Comparable protocol 3. 对符合Comparable协议的Movie类使用sorted()

By making your Movie class conform to Comparable protocol, you can use Array's sorted() method as an alternative to sorted(by:​) .通过使您的Movie类符合Comparable协议,您可以使用 Array 的sorted()方法作为sorted(by:​)的替代方法。

Movie class declaration: Movie类声明:

import Foundation

class Movie: CustomStringConvertible, Comparable {

    let name: String
    var date: Date
    var description: String { return name }

    init(name: String, date: Date = Date()) {
        self.name = name
        self.date = date
    }

    static func ==(lhs: Movie, rhs: Movie) -> Bool {
        return lhs.name == rhs.name
    }

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

}

Usage:用法:

let avatarMovie = Movie(name: "Avatar")
let titanicMovie = Movie(name: "Titanic")
let piranhaMovie = Movie(name: "Piranha II: The Spawning")

let movies = [avatarMovie, titanicMovie, piranhaMovie]
let sortedMovies = movies.sorted()

print(sortedMovies)

/*
 prints: [Avatar, Piranha II: The Spawning, Titanic]
 */
let sortArray =  array.sorted(by: { $0.name.lowercased() < $1.name.lowercased() })

对于那些使用 Swift 3 的人,接受答案的等效方法是:

movieArr.sorted { $0.Name < $1.Name }

Most of these answers are wrong due to the failure to use a locale based comparison for sorting.由于未能使用基于语言环境的比较进行排序,这些答案中的大多数都是错误的。 Look at localizedStandardCompare()看看 localizedStandardCompare()

排序数组 Swift 4.2

arrayOfRaces = arrayOfItems.sorted(by: { ($0["raceName"] as! String) < ($1["raceName"] as! String) })
*import Foundation
import CoreData


extension Messages {

    @nonobjc public class func fetchRequest() -> NSFetchRequest<Messages> {
        return NSFetchRequest<Messages>(entityName: "Messages")
    }

    @NSManaged public var text: String?
    @NSManaged public var date: Date?
    @NSManaged public var friends: Friends?

}

    //here arrMessage is the array you can sort this array as under bellow 

    var arrMessages = [Messages]()

    arrMessages.sort { (arrMessages1, arrMessages2) -> Bool in
               arrMessages1.date! > arrMessages2.date!
    }*

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM