Bagaimana cara menggabungkan atau menggabungkan array di Swift?

396

Jika ada dua array dibuat dengan cepat seperti ini:

var a:[CGFloat] = [1, 2, 3]
var b:[CGFloat] = [4, 5, 6]

Bagaimana mereka bisa digabungkan [1, 2, 3, 4, 5, 6]?

Hristo
sumber
Ini adalah bagian dari stackoverflow.com/q/24465281/78336
neoneye

Jawaban:

691

Anda dapat menggabungkan array dengan +, membangun array baru

let c = a + b
print(c) // [1.0, 2.0, 3.0, 4.0, 5.0, 6.0]

atau menambahkan satu array ke array lainnya dengan +=(atau append):

a += b

// Or:
a.append(contentsOf: b)  // Swift 3
a.appendContentsOf(b)    // Swift 2
a.extend(b)              // Swift 1.2

print(a) // [1.0, 2.0, 3.0, 4.0, 5.0, 6.0]
Martin R
sumber
[AnyObect]? tidak identik dengan CGFloat. Saat bergabung ke array AnyObject.
khunshan
6
Khunshan: AnyObjectmenunjukkan objek, yang seperti yang saya mengerti berarti sesuatu yang dipakai dari tipe kelas. CGFloatbukan objek, ini adalah nilai skalar. Seperti yang saya pahami, array dapat mengandung skalar, kecuali jika didefinisikan sebagai mengandung AnyObjectatau disempurnakan lebih lanjut. Namun, saya curiga di sini masalahnya adalah bahwa array dibungkus dengan opsional, jadi Anda harus membukanya dengan !atau ?pertama.
Owen Godfrey
Apakah kita tahu apakah kecerdasan Swift 2 Copy-On-Write meluas untuk menentukan apakah bbagian ayang dimodifikasi (karena itu mungkin memilih salinan bselama a.appendContentsOf(b))?
Ephemera
1
@WenGodfrey terima kasih. saya punya sedikit kebingungan atas appendContentsOf dan insertContentsOf.
khunshan
137

Dengan Swift 5, sesuai dengan kebutuhan Anda, Anda dapat memilih salah satu dari enam cara berikut untuk menggabungkan / menggabungkan dua array.


# 1. Menggabungkan dua array ke array baru dengan Array's+(_:_:) Operator generik

Arraymemiliki +(_:_:)operator generik. +(_:_:)memiliki deklarasi berikut :

Membuat koleksi baru dengan menggabungkan elemen-elemen koleksi dan urutan.

static func + <Other>(lhs: Array<Element>, rhs: Other) -> Array<Element> where Other : Sequence, Self.Element == Other.Element

Kode sampel Playground berikut menunjukkan cara menggabungkan dua array tipe [Int]ke array baru menggunakan +(_:_:)operator generik:

let array1 = [1, 2, 3]
let array2 = [4, 5, 6]

let flattenArray = array1 + array2
print(flattenArray) // prints [1, 2, 3, 4, 5, 6]

# 2. Menambahkan elemen array ke array yang ada dengan Array's+=(_:_:) Operator generik

Arraymemiliki +=(_:_:)operator generik. +=(_:_:)memiliki deklarasi berikut :

Menambahkan elemen urutan ke koleksi yang dapat diganti jangkauan.

static func += <Other>(lhs: inout Array<Element>, rhs: Other) where Other : Sequence, Self.Element == Other.Element

Kode sampel Playground berikut menunjukkan cara menambahkan elemen dari array tipe [Int]ke array yang ada menggunakan +=(_:_:)operator generik:

var array1 = [1, 2, 3]
let array2 = [4, 5, 6]

array1 += array2
print(array1) // prints [1, 2, 3, 4, 5, 6]

# 3. Menambahkan array ke array yang lain dengan Array'sappend(contentsOf:) metode

Swift Arraypunya append(contentsOf:)metode. append(contentsOf:)memiliki deklarasi berikut :

Menambahkan elemen urutan atau koleksi ke akhir koleksi ini.

mutating func append<S>(contentsOf newElements: S) where S : Sequence, Self.Element == S.Element

Kode sampel Playground berikut menunjukkan cara menambahkan array ke array tipe lain [Int]menggunakan append(contentsOf:)metode:

var array1 = [1, 2, 3]
let array2 = [4, 5, 6]

array1.append(contentsOf: array2)
print(array1) // prints [1, 2, 3, 4, 5, 6]

# 4 Menggabungkan dua array ke array baru dengan Sequence'sflatMap(_:) metode

Swift menyediakan flatMap(_:)metode untuk semua jenis yang sesuai dengan Sequenceprotokol (termasuk Array). flatMap(_:)memiliki deklarasi berikut :

Mengembalikan array yang berisi hasil gabungan dari panggilan transformasi yang diberikan dengan setiap elemen dari urutan ini.

func flatMap<SegmentOfResult>(_ transform: (Self.Element) throws -> SegmentOfResult) rethrows -> [SegmentOfResult.Element] where SegmentOfResult : Sequence

Kode sampel Playground berikut ini menunjukkan cara menggabungkan dua array tipe [Int]ke array baru menggunakan flatMap(_:)metode:

let array1 = [1, 2, 3]
let array2 = [4, 5, 6]

let flattenArray = [array1, array2].flatMap({ (element: [Int]) -> [Int] in
    return element
})
print(flattenArray) // prints [1, 2, 3, 4, 5, 6]

# 5 Menggabungkan dua array ke array baru dengan Sequence's joined()metode dan Array' sinit(_:) initializer

Swift menyediakan joined()metode untuk semua jenis yang sesuai dengan Sequenceprotokol (termasuk Array). joined()memiliki deklarasi berikut :

Mengembalikan elemen dari urutan urutan ini, disatukan.

func joined() -> FlattenSequence<Self>

Selain itu, Swift Arraymemiliki init(_:)inisialisasi. init(_:)memiliki deklarasi berikut :

Membuat array berisi elemen-elemen dari suatu urutan.

init<S>(_ s: S) where Element == S.Element, S : Sequence

Oleh karena itu, kode sampel Playground berikut menunjukkan cara menggabungkan dua array tipe [Int]ke array baru menggunakan joined()metode dan init(_:)penginisialisasi:

let array1 = [1, 2, 3]
let array2 = [4, 5, 6]

let flattenCollection = [array1, array2].joined() // type: FlattenBidirectionalCollection<[Array<Int>]>
let flattenArray = Array(flattenCollection)
print(flattenArray) // prints [1, 2, 3, 4, 5, 6]

# 6. Menggabungkan dua array ke array baru dengan Array'sreduce(_:_:) metode

Swift Arraypunya reduce(_:_:)metode. reduce(_:_:)memiliki deklarasi berikut :

Mengembalikan hasil menggabungkan elemen-elemen dari urutan menggunakan penutupan yang diberikan.

func reduce<Result>(_ initialResult: Result, _ nextPartialResult: (Result, Element) throws -> Result) rethrows -> Result

Kode Playground berikut menunjukkan cara menggabungkan dua array tipe [Int]ke array baru menggunakan reduce(_:_:)metode:

let array1 = [1, 2, 3]
let array2 = [4, 5, 6]

let flattenArray = [array1, array2].reduce([], { (result: [Int], element: [Int]) -> [Int] in
    return result + element
})
print(flattenArray) // prints [1, 2, 3, 4, 5, 6]
Imanou Petit
sumber
5
terima kasih telah berbagi kode ini, penjelasan yang baik, hanya saran untuk jawaban Anda, akan lebih baik, jika Anda mengatakan yang mana yang lebih efisien dengan kinerja?
kokemomuke
Saya suka +untuk 2 array dan joined()untuk array array.
Cœur
Jika Anda menggabungkan lebih dari 2 array (atau string atau apa pun), menahan diri dari menggunakan +operator, itu menghasilkan waktu kompilasi yang benar-benar gila.
Lawicko
@ lawicko metode apa yang akan Anda rekomendasikan?
CyberMew
@CyberMew Apa pun yang tidak menggunakan operator kelebihan beban, saya suka metode # 3 karena saya pikir itu paling mudah dibaca, tapi saya juga suka metode # 4 dengan peta datar. Untuk string saya suka metode # 5 karena pada akhirnya Anda mendapatkan string yang bergabung segera.
lawicko
34

Jika Anda bukan penggemar berat overloading operator, atau hanya lebih dari tipe fungsional:

// use flatMap
let result = [
    ["merge", "me"], 
    ["We", "shall", "unite"],
    ["magic"]
].flatMap { $0 }
// Output: ["merge", "me", "We", "shall", "unite", "magic"]

// ... or reduce
[[1],[2],[3]].reduce([], +)
// Output: [1, 2, 3]
Mazyod
sumber
22

Metode favorit saya sejak Swift 2.0 rata

var a:[CGFloat] = [1, 2, 3]
var b:[CGFloat] = [4, 5, 6]

let c = [a, b].flatten()

Ini akan kembali FlattenBidirectionalCollectionjadi jika Anda hanya menginginkan CollectionTypeini akan cukup dan Anda akan memiliki evaluasi malas secara gratis. Jika Anda benar-benar membutuhkan Array, Anda dapat melakukan ini:

let c = Array([a, b].flatten())
Tomasz Bąk
sumber
2
flatten()sepertinya tidak ada lagi saat ini. Tetapi Anda dapat mempertimbangkan joined().
Cœur
13

Untuk melengkapi daftar alternatif yang memungkinkan, reducedapat digunakan untuk menerapkan perilaku perataan :

var a = ["a", "b", "c"] 
var b = ["d", "e", "f"]

let res = [a, b].reduce([],combine:+)

Alternatif terbaik (kinerja / memori-bijaksana) di antara yang disajikan adalah sederhana flatten, yang hanya membungkus array asli dengan malas tanpa membuat struktur array baru.

Tetapi perhatikan bahwa perataan tidak mengembalikan aLazyCollection , sehingga perilaku malas tidak akan disebarkan ke operasi berikutnya di sepanjang rantai (peta, flatMap, filter, dll ...).

Jika lazyness masuk akal dalam kasus tertentu, hanya ingat untuk tambahkan atau menambahkan sebuah .lazyuntuk flatten(), misalnya, memodifikasi Tomasz sampel dengan cara ini:

let c = [a, b].lazy.flatten()
Umberto Raimondi
sumber
Seberapa baik jawaban ini masih bertahan pada 2019 dengan Swift 5.1?
willbattel
flatten () tidak ada lagi. bergabung () dapat digunakan sebagai pengganti rata ()
Pranav Pravakar
4

Jika Anda ingin array kedua dimasukkan setelah indeks tertentu, Anda dapat melakukan ini (pada Swift 2.2):

let index = 1
if 0 ... a.count ~= index {
     a[index..<index] = b[0..<b.count]
}
print(a) // [1.0, 4.0, 5.0, 6.0, 2.0, 3.0] 
Vitalii
sumber
4

Swift 3.0

Anda dapat membuat array baru dengan menambahkan bersama dua array yang ada dengan tipe yang kompatibel dengan operator tambahan ( +). Jenis array baru disimpulkan dari jenis dua array yang Anda tambahkan bersama,

let arr0 = Array(repeating: 1, count: 3) // [1, 1, 1]
let arr1 = Array(repeating: 2, count: 6)//[2, 2, 2, 2, 2, 2]
let arr2 = arr0 + arr1 //[1, 1, 1, 2, 2, 2, 2, 2, 2]

ini adalah hasil yang benar dari kode di atas.

Lorem Ipsum Dolor
sumber
4
var arrayOne = [1,2,3]
var arrayTwo = [4,5,6]

jika Anda ingin hasilnya sebagai: [1,2,3, [4,5,6]]

arrayOne.append(arrayTwo)

kode di atas akan mengonversi arrayOne sebagai elemen tunggal dan menambahkannya ke akhir arrayTwo.

jika Anda ingin hasilnya sebagai: [1, 2, 3, 4, 5, 6] maka,

arrayOne.append(contentsOf: arrayTwo)

kode di atas akan menambahkan semua elemen arrayOne di akhir arrayTwo.

Terima kasih.

meMadhav
sumber
4

Swift 4.X

Cara termudah yang saya tahu adalah dengan hanya menggunakan tanda +

var Array1 = ["Item 1", "Item 2"]
var Array2 = ["Thing 1", "Thing 2"]

var Array3 = Array1 + Array2

// Array 3 will just be them combined :)
Stotch
sumber
3

Inilah cara terpendek untuk menggabungkan dua array.

 var array1 = [1,2,3]
 let array2 = [4,5,6]

Menggabungkan / menggabungkan mereka

array1 += array2
New value of array1 is [1,2,3,4,5,6]
pegangan tangan
sumber
1

Demikian pula, dengan kamus array, orang dapat:

var dict1 = [String:[Int]]()
var dict2 = [String:[Int]]()
dict1["key"] = [1,2,3]
dict2["key"] = [4,5,6]
dict1["key"] = dict1["key"]! + dict2["key"]!
print(dict1["key"]!)

dan Anda dapat mengulangi dict1 dan menambahkan dict2 jika "kunci" cocok

Jeremy Andrews
sumber
0

Marge array yang merupakan tipe data yang berbeda:

var arrayInt = [Int]()
arrayInt.append(6)
var testArray = ["a",true,3,"b"] as [Any]
testArray.append(someInt)

Keluaran:

["a", true, 3, "b", "hi", 3, [6]]
Abhishek Gupta
sumber