排序通过数组排除零

时间:2016-10-19 19:55:08

标签: arrays swift sorting

我正在尝试对包含nil变量的数组进行排序。

class TestArray {
    var a: String? = nil
    var b: String? = nil
    init(a: String?, b: String?) {
        self.a = a
        self.b = b
    }
}

let first = TestArray(a: "xxx", b: "yyy")
let second = TestArray(a: "zzz", b: "zzz")
let third = TestArray(a: "aaa", b: nil)

var array = [first, second, third]
array.sort(by: {($0.a as String!) > ($1.a as String!)})

array.sort(by: {($0.b as String!) > ($1.b as String!)}) // Throws an error

如何按b排序并在数组末尾保留第三个TestArray,其中b = nil? 此外,我想对所有b进行排序,然后对于其中b = nil的数组进行排序,其余为a。

3 个答案:

答案 0 :(得分:3)

我相信这应该涵盖你想要的情况,而不必多次迭代(这是昂贵的)

    check_classification_targets(y)

    # actual graph construction (implementations should override this)
    graph_matrix = self._build_graph()

    # label construction
    # construct a categorical distribution for classification only
    classes = np.unique(y)
    classes = (classes[classes != -1])

答案 1 :(得分:2)

这里(在我看来)最好的方式:

首先,我为<个实例定义了一个String?运算符。 它适用于nil比较任何其他字符串的规范,因此它会按排序顺序显示 first

fileprivate func <(a: String?, b: String?) -> Bool {
    switch (a, b) {
        case (nil, nil): return false
        case (nil, _?): return true
        case (_?, nil): return false
        case (let a?, let b?): return a < b

    }
}

接下来,我编写了一个使用该运算符的排序谓词。它适用于实例首先按其a排序的规范。如果这些是平等的,那么通过按b排序来打破关系。

struct TestStruct {
    var a: String?
    var b: String?
}

let input = [  
    TestStruct(a: "xxx", b: "yyy"),
    TestStruct(a: "zzz", b: "zzz"),
    TestStruct(a: "aaa", b: nil)
]

let output = input.sorted { lhs, rhs in
    if lhs.a != rhs.a { return lhs.a < rhs.a } // first sort by a
    if lhs.b != rhs.b { return lhs.b < rhs.b } // then sort by b

    return true
}

print(output)
//[
//    TempCode.TestStruct(a: Optional("aaa"), b: nil),
//    TempCode.TestStruct(a: Optional("xxx"), b: Optional("yyy")),
//    TempCode.TestStruct(a: Optional("zzz"), b: Optional("zzz"))
//]

*我使TestStruct成为一个结构,因此我可以使用合成的初始化程序和自动打印行为。如果它是一个类,它的工作方式也一样。

如果您要对TestStruct进行大量比较,并且有一个标准订单来比较它是有意义的,那么您最好将符合性添加到Comparable 。这样做还需要符合Equatable

extension TestStruct: Equatable {
    public static func ==(lhs: TestStruct, rhs: TestStruct) -> Bool {
        return
            lhs.a == rhs.a &&
            lhs.b == rhs.b
    }
}

extension TestStruct: Comparable {
    public static func <(lhs: TestStruct, rhs: TestStruct) -> Bool {
        if lhs.a != rhs.a { return lhs.a < rhs.a } // first sort by a
        if lhs.b != rhs.b { return lhs.b < rhs.b } // then sort by b

        return true
    }
}

现在,您可以使用TestStruct指定的排序行为轻松地对数组进行排序:

let output = input.sorted()

You can see it in action here.

答案 2 :(得分:1)

如果您不一定需要进行排序,您可以简单地应用您描述的“算法”,以便使用array后面的filter sortedb进行排序对于子集阵列。

“算法”:

  • 主要按nil属性排序,因为它不是b
  • 对于nil属性为a的元素,请按a属性排序。
  • 在排序数组的末尾留下bnil都为// lets set up a more interesting example let first = TestArray(a: "xxx", b: "yyy") let second = TestArray(a: "ccc", b: nil) let third = TestArray(a: "aaa", b: nil) let fourth = TestArray(a: "zzz", b: "zzz") let fifth = TestArray(a: "bbb", b: nil) var array = [first, second, third, fourth, fifth] let sorted = array.filter { $0.b != nil }.sorted { $0.b! < $1.b! } + array.filter { $0.b == nil && $0.a != nil }.sorted { $0.a! < $1.a! } + array.filter { $0.b == nil && $0.a == nil } sorted.enumerated().forEach { print("\($0): b: \($1.b), a: \($1.a)") } /* 0: b: Optional("yyy"), a: Optional("xxx") 1: b: Optional("zzz"), a: Optional("zzz") 2: b: nil, a: Optional("aaa") 3: b: nil, a: Optional("bbb") 4: b: nil, a: Optional("ccc") */ 的元素。

E.g:

select