- Published on
Swiftda map, filter, reduce, compactMap, flatMap
- Authors
- Name
- ShoxruxC
- @iOSdasturchi
Higher-Order Functions
Higher-Order Function — boshqa funksiyani parametr sifatida qabul qiladigan yoki qaytaradigan funksiya. Swift da map, filter, reduce, compactMap, flatMap — bular funksional dasturlashning asosi. Ular for loop o'rniga qisqa, ifodali va xavfsiz kod yozish imkonini beradi. Asosiy afzallik: asl massiv o'zgarmaydi — har doim yangi natija qaytariladi.
map() — o'zgartirish
map() — massivdagi har bir elementni berilgan funksiya bilan o'zgartiradi va yangi massiv qaytaradi. Asl massiv o'zgarmaydi. $0 — closure ning birinchi parametri uchun qisqartma.
// ═══════════════════════════════════════
// MAP — har elementni o'zgartiradi
// ═══════════════════════════════════════
let sonlar = [1, 2, 3, 4, 5]
// for loop bilan:
var ikkilangan: [Int] = []
for son in sonlar {
ikkilangan.append(son * 2)
}
// map bilan — bitta qatorda:
let ikkilanganMap = sonlar.map { $0 * 2 }
// [2, 4, 6, 8, 10]
// String ga aylantirish
let matnlar = sonlar.map { "Son: \($0)" }
// ["Son: 1", "Son: 2", "Son: 3", "Son: 4", "Son: 5"]
// Struct lar bilan
struct Talaba { let ism: String; let baho: Int }
let talabalar = [Talaba(ism: "Ali", baho: 5), Talaba(ism: "Vali", baho: 4)]
let ismlar = talabalar.map { $0.ism } // ["Ali", "Vali"]
let baholar = talabalar.map { $0.baho } // [5, 4]
filter() — tanlash
filter() — berilgan shartga mos keladigan elementlarni tanlab, yangi massiv qaytaradi. Closure Bool qaytarishi kerak — true bo'lsa element saqlanadi, false bo'lsa tashlab yuboriladi.
// ═══════════════════════════════════════
// FILTER — shartga mos elementlarni tanlash
// ═══════════════════════════════════════
let sonlar = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
let juftlar = sonlar.filter { $0 % 2 == 0 } // [2, 4, 6, 8, 10]
let kattalar = sonlar.filter { $0 > 5 } // [6, 7, 8, 9, 10]
// Struct bilan
let yaxshiTalabalar = talabalar.filter { $0.baho >= 4 }
// Matn bilan
let ismlar = ["Ali", "Vali", "Anvar", "Akbar"]
let aBilan = ismlar.filter { $0.hasPrefix("A") } // ["Ali", "Anvar", "Akbar"]
reduce() — yig'ish
reduce() — barcha elementlarni bitta qiymatga yig'adi. Birinchi parametr — boshlang'ich qiymat, ikkinchi parametr — har iteratsiyada natijani qanday hisoblash. Yig'indi, ko'paytma, matnlarni birlashtirish, eng katta qiymat topish — barchasi reduce bilan.
// ═══════════════════════════════════════
// REDUCE — barcha elementlarni bitta qiymatga
// ═══════════════════════════════════════
let sonlar = [1, 2, 3, 4, 5]
// Yig'indi
let yigindi = sonlar.reduce(0) { natija, element in
natija + element
}
// 0 + 1 + 2 + 3 + 4 + 5 = 15
// Qisqa yozuv
let yigindiQisqa = sonlar.reduce(0, +) // 15
// Ko'paytma
let kopaytma = sonlar.reduce(1, *) // 120
// Matn birlashtirish
let ismlar = ["Ali", "Vali", "Gani"]
let birlashgan = ismlar.reduce("") { $0 + ($0.isEmpty ? "" : ", ") + $1 }
// "Ali, Vali, Gani"
// Eng katta son topish
let eng_katta = sonlar.reduce(Int.min) { max($0, $1) } // 5
compactMap() — nil larni olib tashlash
compactMap() — map kabi ishlaydi, lekin natijada nil bo'lganlarni avtomatik olib tashlaydi. Bu Optional qaytaradigan transformatsiya uchun ideal. Masalan, Int("ikki") nil qaytaradi — compactMap uni tashlab yuboradi.
// ═══════════════════════════════════════
// COMPACTMAP — map + nil olib tashlash
// ═══════════════════════════════════════
let matnlar = ["1", "ikki", "3", "to'rt", "5"]
// map — Optional qaytaradi
let mapNatija = matnlar.map { Int($0) }
// [Optional(1), nil, Optional(3), nil, Optional(5)]
// compactMap — nil larni olib tashlaydi
let sonlar = matnlar.compactMap { Int($0) }
// [1, 3, 5] — faqat muvaffaqiyatli konvertatsiyalar
// Amaliy misol — email validatsiya
let kiritimlar = ["ali@mail.com", "xato", "vali@mail.com", "123", "gani@mail.com"]
let emaillar = kiritimlar.compactMap { matn -> String? in
matn.contains("@") ? matn : nil
}
// ["ali@mail.com", "vali@mail.com", "gani@mail.com"]
flatMap() — tekislash
flatMap() — ichma-ich massivlarni bitta tekis massivga aylantiradi. [[1,2],[3,4]] → [1,2,3,4]. Amaliy misol: har talabaning fanlarini bitta umumiy ro'yxatga yig'ish.
// ═══════════════════════════════════════
// FLATMAP — ichma-ich massivlarni tekislash
// ═══════════════════════════════════════
let ichmaIch = [[1, 2, 3], [4, 5], [6, 7, 8, 9]]
let tekis = ichmaIch.flatMap { $0 }
// [1, 2, 3, 4, 5, 6, 7, 8, 9]
// Amaliy misol — har talabaning fanlarini yig'ish
struct Talaba {
let ism: String
let fanlar: [String]
}
let talabalar = [
Talaba(ism: "Ali", fanlar: ["Matematika", "Fizika"]),
Talaba(ism: "Vali", fanlar: ["Kimyo", "Biologiya", "Matematika"]),
]
let barcha_fanlar = talabalar.flatMap { $0.fanlar }
// ["Matematika", "Fizika", "Kimyo", "Biologiya", "Matematika"]
let noyob_fanlar = Set(barcha_fanlar)
// {"Matematika", "Fizika", "Kimyo", "Biologiya"}
Zanjir (chaining)
Bir nechta higher-order funksiyani ketma-ket ulash mumkin. Masalan: .filter().map().sorted() — bitta ifodada filtrlash, o'zgartirish va tartiblash. Bu kod juda ifodali va o'qish oson.
// ═══════════════════════════════════════
// ZANJIR — bir nechta funksiyani ulash
// ═══════════════════════════════════════
struct Mahsulot {
let nomi: String
let narxi: Double
let omborda: Bool
}
let mahsulotlar = [
Mahsulot(nomi: "iPhone", narxi: 999, omborda: true),
Mahsulot(nomi: "MacBook", narxi: 1999, omborda: false),
Mahsulot(nomi: "iPad", narxi: 799, omborda: true),
Mahsulot(nomi: "AirPods", narxi: 249, omborda: true),
]
// Bitta ifodada: omborda borlar → nomini ol → tartiblash
let natija = mahsulotlar
.filter { $0.omborda } // Faqat ombordagilar
.map { $0.nomi } // Faqat nomlarini ol
.sorted() // Alifbo tartibida
// ["AirPods", "iPad", "iPhone"]
// Ombordagi mahsulotlarning umumiy narxi
let umumiyNarx = mahsulotlar
.filter { $0.omborda }
.map { $0.narxi }
.reduce(0, +)
// 999 + 799 + 249 = 2047
🎯 Topshiriq
Talabalar massivi yarating (ism, baho, fan). filter bilan baho >= 4 oling. map bilan faqat ismlarini oling. reduce bilan baholar yig'indisini hisoblang. compactMap bilan optional holatni qayta ishlang. Barchasini zanjir qilib bitta ifodada yozing.