加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 百科 > 正文

数组 – 在两个元素的数组中拆分大数组

发布时间:2020-12-14 05:43:20 所属栏目:百科 来源:网络整理
导读:我有大量的对象列表,我需要将它们分成一组两个元素用于UI propouse. 例: [0,1,2,3,4,5,6] 成为这四个数组的数组 [[0,1],[2,3],[4,5],[6]] 分割阵列有很多种方法.但是,如果阵列很大,那么效率最高(成本最低)的是什么. 如果你正在寻找效率,你可以有一个方法,可
我有大量的对象列表,我需要将它们分成一组两个元素用于UI propouse.

例:

[0,1,2,3,4,5,6]

成为这四个数组的数组

[[0,1],[2,3],[4,5],[6]]

分割阵列有很多种方法.但是,如果阵列很大,那么效率最高(成本最低)的是什么.

如果你正在寻找效率,你可以有一个方法,可以懒惰地生成每个2个元素的数组,所以你一次只能在内存中存储2个元素:
public struct ChunkGen<G : GeneratorType> : GeneratorType {

  private var g: G
  private let n: Int
  private var c: [G.Element]

  public mutating func next() -> [G.Element]? {
    var i = n
    return g.next().map {
      c = [$0]
      while --i > 0,let next = g.next() { c.append(next) }
      return c
    }
  }

  private init(g: G,n: Int) {
    self.g = g
    self.n = n
    self.c = []
    self.c.reserveCapacity(n)
  }
}

public struct ChunkSeq<S : SequenceType> : SequenceType {

  private let seq: S
  private let n: Int

  public func generate() -> ChunkGen<S.Generator> {
    return ChunkGen(g: seq.generate(),n: n)
  }
}

public extension SequenceType {
  func chunk(n: Int) -> ChunkSeq<Self> {
    return ChunkSeq(seq: self,n: n)
  }
}

var g = [1,5].chunk(2).generate()

g.next() // [1,2]
g.next() // [3,4]
g.next() // [5]
g.next() // nil

此方法适用于任何SequenceType,而不仅仅是Arrays.

对于Swift 1,没有协议扩展,你有:

public struct ChunkGen<T> : GeneratorType {

  private var (st,en): (Int,Int)
  private let n: Int
  private let c: [T]

  public mutating func next() -> ArraySlice<T>? {
    (st,en) = (en,en + n)
    return st < c.endIndex ? c[st..<min(en,c.endIndex)] : nil
  }

  private init(c: [T],n: Int) {
    self.c = c
    self.n = n
    self.st = 0 - n
    self.en = 0
  }
}

public struct ChunkSeq<T> : SequenceType {

  private let c: [T]
  private let n: Int

  public func generate() -> ChunkGen<T> {
    return ChunkGen(c: c,n: n)
  }
}

func chunk<T>(ar: [T],#n: Int) -> ChunkSeq<T> {
  return ChunkSeq(c: ar,n: n)
}

对于Swift 3:

public struct ChunkIterator<I: IteratorProtocol> : IteratorProtocol {

  fileprivate var i: I
  fileprivate let n: Int

  public mutating func next() -> [I.Element]? {
    guard let head = i.next() else { return nil }
    var build = [head]
    build.reserveCapacity(n)
    for _ in (1..<n) {
      guard let x = i.next() else { break }
      build.append(x)
    }
    return build
  }

}

public struct ChunkSeq<S: Sequence> : Sequence {

  fileprivate let seq: S
  fileprivate let n: Int

  public func makeIterator() -> ChunkIterator<S.Iterator> {
    return ChunkIterator(i: seq.makeIterator(),n: n)
  }
}

public extension Sequence {
  func chunk(_ n: Int) -> ChunkSeq<Self> {
    return ChunkSeq(seq: self,5].chunk(2).makeIterator()

g.next() // [1,4]
g.next() // [5]
g.next() // nil

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读