IlmHamroh
JavaScript Full-stack/8-qism. JavaScript asoslari33/61-dars14 daqiqa
Mundarija (28)

JavaScript switch: bitta qiymatni ko'p variant bilan solishtirish

Qisqacha: switch bitta qiymatni bir nechta variant bilan solishtiradi va mos kelgan case dan boshlab kodni bajaradi. Solishtirish qat'iy tenglik === bilan bo'ladi. Har case oxiriga break qo'yiladi, aks holda kod keyingi case ga "oqib" o'tadi. Hech bir variant mos kelmasa, default bloki ishlaydi.

Bu darsda

  • switch, case, break va default bilan ko'p variantli tanlov yoza olasiz.
  • break unutilganda nima bo'lishini (fall-through) tushuntira olasiz va undan ataylab foydalana olasiz.
  • Bir nechta case ni bitta natijaga guruhlay olasiz.
  • switch (true) naqshini taniysiz va uning kamchiligini bilasiz.
  • switch, else if va obyekt-lug'atdan qaysi biri qachon qulayligini ajrata olasiz.

Oldin bilishingiz kerak: if / else if / else, Tenglik: ==, === va Object.is, Ternary operatori.

1. Nega bu kerak?

Oldingi darsda else if zanjirini o'rgandik. Endi Telegram bot yozyapmiz deylik. Foydalanuvchi buyruq yuboradi, bot esa har buyruqqa o'z javobini beradi:

js
const buyruq = "/narx";

if (buyruq === "/start") {
  console.log("Xush kelibsiz!");
} else if (buyruq === "/narx") {
  console.log("Kurs bepul!");
} else if (buyruq === "/yordam") {
  console.log("Buyruqlar: /start, /narx, /yordam");
} else {
  console.log("Bunday buyruq yo'q");
}

Konsolda:

text
Kurs bepul!

Kod ishlaydi. Lekin buyruq === uch marta takrorlandi. Buyruqlar 10 ta bo'lsa — 10 marta. Har qatorda bitta o'zgaruvchi, faqat qiymati boshqa.

Bunday holat — bitta qiymatni ko'p variant bilan solishtirish — juda ko'p uchraydi. Uning uchun JavaScript'da maxsus ko'rsatma bor: switch.

2. switch qanday ishlaydi

2.1 Birinchi misol

Xuddi shu botni switch bilan yozamiz:

js
const buyruq = "/narx";

switch (buyruq) {
  case "/start":
    console.log("Xush kelibsiz!");
    break;
  case "/narx":
    console.log("Kurs bepul!");
    break;
  case "/yordam":
    console.log("Buyruqlar: /start, /narx, /yordam");
    break;
  default:
    console.log("Bunday buyruq yo'q");
}

Konsolda:

text
Kurs bepul!

Natija bir xil. Lekin endi solishtirilayotgan qiymat (buyruq) faqat bir marta, eng tepada yozilgan. Pastda esa faqat variantlar ro'yxati.

Hayotdan o'xshatish: ichimlik avtomati. Raqamni terasiz — masalan, 12. Avtomat katak raqamlarini birma-bir ko'rib chiqadi va aynan 12-katakni ochadi. Bunday raqam bo'lmasa, ekranda "Xato raqam" chiqadi — bu default.

2.2 Qismlari

js
switch (qiymat) {
  case variant1:
    // qiymat === variant1 bo'lsa
    break;
  case variant2:
    // qiymat === variant2 bo'lsa
    break;
  default:
    // hech biri mos kelmasa
}
  • switch (qiymat) — solishtiriladigan qiymat. Oddiy qavs ichida, xuddi if dagidek.
  • case "/start": — bitta variant. Oxirida ikki nuqta : turadi. Undan keyingi qatorlar shu variantga tegishli.
  • break — "to'xta, switch dan chiq". Keyingi case larga o'tmaslik uchun kerak.
  • default: — "qolgan hamma holat". else ga o'xshaydi. Majburiy emas.

JavaScript qanday ishlaydi: qavsdagi qiymatni oladi va case larni yuqoridan pastga solishtiradi. Birinchi mos kelgan case dan boshlab kodni bajaradi. break ga yetganda switch dan chiqib ketadi.

Maslahat: default oxirida bo'lsa, undan keyin break shart emas — baribir switch tugaydi. Ko'p jamoalar default ni doim oxirida yozadi va doim qo'yadi. Shunda kutilmagan qiymat jimgina o'tib ketmaydi.

2.3 Solishtirish — faqat ===

switch qiymatlarni qat'iy tenglik === bilan solishtiradi. Ya'ni tur ham mos kelishi kerak.

Bu tuzoqqa olib keladi. Formadan yoki terminaldan kelgan ma'lumot deyarli doim satr bo'ladi:

js
const tanlov = "2";

switch (tanlov) {
  case 1:
    console.log("Ekonom tarif");
    break;
  case 2:
    console.log("Komfort tarif");
    break;
  default:
    console.log("Noma'lum tarif");
}

Konsolda:

text
Noma'lum tarif

"2" === 2 — false, chunki biri satr, biri son. switch uchun ular boshqa-boshqa qiymat. Tuzatish — qiymatni oldindan kerakli turga aylantirish: switch (Number(tanlov)). Yoki case larni satr qilib yozish: case "2":. Turlarni aniq o'zgartirish shu yerda asqotadi.

Tekshirib ko'ring: switch (tanlov) da tanlov = 2 (son) bo'lsa va case "2": yozilgan bo'lsa, u ishlaydimi?

Javob

Yo'q, ishlamaydi. 2 === "2" — false. switch hech qachon turlarni aylantirmaydi — == emas, doim ===. Qiymat va case bir xil turda bo'lishi kerak.

3. break va "oqib o'tish"

3.1 break unutilsa nima bo'ladi?

Bu switch ning eng mashhur tuzog'i. break larni olib tashlaymiz:

js
const buyruq = "/start";

switch (buyruq) {
  case "/start":
    console.log("Xush kelibsiz!");
  case "/narx":
    console.log("Kurs bepul!");
  case "/yordam":
    console.log("Buyruqlar: /start, /narx, /yordam");
  default:
    console.log("Bunday buyruq yo'q");
}

Konsolda:

text
Xush kelibsiz!
Kurs bepul!
Buyruqlar: /start, /narx, /yordam
Bunday buyruq yo'q

Foydalanuvchi faqat /start yubordi, bot esa to'rt xil javob berdi! switch mos case ni topgach, pastga qarab hamma kodni bajaraveradi. Boshqa case larni tekshirmaydi ham. U faqat break yoki switch oxiriga yetganda to'xtaydi.

Bu hodisa oqib o'tish (fall-through) deyiladi. Hayotdan o'xshatish: bekatda to'xtashni so'ramagan avtobus. Siz o'z bekatingizda tushmoqchi edingiz, lekin haydovchiga aytmadingiz — avtobus oxirgi bekatgacha olib ketdi. break — "shu yerda to'xtang" degan so'z.

3.2 Bir nechta case — bitta natija

Oqib o'tishning foydali tomoni ham bor. Bir nechta variant bir xil natija bersa, ularni ketma-ket yozasiz:

js
const oy = "fevral";
let fasl;

switch (oy) {
  case "dekabr":
  case "yanvar":
  case "fevral":
    fasl = "qish";
    break;
  case "mart":
  case "aprel":
  case "may":
    fasl = "bahor";
    break;
  default:
    fasl = "yoz yoki kuz";
}

console.log(`${oy}: ${fasl}`); // fevral: qish

"fevral" uchinchi case ga mos keldi. Uning ostida kod yo'q, shuning uchun JavaScript pastga oqib, fasl = "qish" ga yetdi. So'ng break. Bo'sh case lar guruhlash uchun juda qulay: ro'yxat ko'rinib turadi.

fasl ni switch dan oldin let bilan yaratdik. Sababini oldingi darsda ko'rgan edik: blok ichida yaratilgan o'zgaruvchi tashqarida ko'rinmaydi.

3.3 Ataylab oqib o'tish

Ba'zan oqib o'tish aynan kerakli narsa. Taksi ilovasida tariflar bor, har yuqori tarif pastkisining hamma qulayliklarini ham o'z ichiga oladi:

js
const tarif = "komfort";

console.log(`"${tarif}" tarifida:`);

switch (tarif) {
  case "biznes":
    console.log("- Bepul suv");
  // break yo'q — ataylab pastga o'tadi
  case "komfort":
    console.log("- Konditsioner");
  // break yo'q — ataylab pastga o'tadi
  case "ekonom":
    console.log("- Xavfsiz haydovchi");
    break;
  default:
    console.log("- Bunday tarif yo'q");
}

Konsolda:

text
"komfort" tarifida:
- Konditsioner
- Xavfsiz haydovchi

"komfort" ikkinchi case ga mos keldi va pastga oqib, "ekonom" ning qulayligini ham chiqardi. "biznes" bo'lsa — uchalasi chiqadi.

Muhim odat: ataylab break qo'ymasangiz, izoh yozing. Aks holda boshqa dasturchi (yoki bir oydan keyin o'zingiz) buni xato deb o'ylab, break qo'shib qo'yadi. ESLint (kodni avtomatik tekshiradigan vosita, kursda keyinroq o'rganamiz) izohsiz oqib o'tishni xato deb belgilaydi.

Tekshirib ko'ring: 3.3-dagi kodda tarif = "ekonom" bo'lsa, konsolda nechta qator chiqadi? tarif = "vip" bo'lsa-chi?

Javob

"ekonom" bo'lsa — 2 qator: sarlavha va - Xavfsiz haydovchi. Undan keyin break bor, default ga o'tilmaydi. "vip" bo'lsa — ham 2 qator: sarlavha va - Bunday tarif yo'q. Hech bir case mos kelmadi, default ishladi.

4. case ichida o'zgaruvchi e'lon qilish

Ikki case da bir xil nomli o'zgaruvchi kerak bo'lib qolsa, kutilmagan xato chiqadi:

js
const tolovTuri = "karta";

switch (tolovTuri) {
  case "naqd":
    let xabar = "Haydovchiga naqd to'lang";
    console.log(xabar);
    break;
  case "karta":
    let xabar = "Kartadan yechiladi";
    console.log(xabar);
    break;
}
text
SyntaxError: Identifier 'xabar' has already been declared

Tarjimasi: "xabar nomi allaqachon e'lon qilingan". Nega? Chunki butun switch — bitta blok, uning jingalak qavslari bitta. case lar alohida blok emas, shunchaki "belgi". Bitta blokda bitta nomni ikki marta let bilan e'lon qilib bo'lmaydi.

Tuzatish — har case ichini o'z jingalak qavsiga olish:

js
const tolovTuri = "karta";

switch (tolovTuri) {
  case "naqd": {
    let xabar = "Haydovchiga naqd to'lang";
    console.log(xabar);
    break;
  }
  case "karta": {
    let xabar = "Kartadan yechiladi";
    console.log(xabar);
    break;
  }
}

Konsolda:

text
Kartadan yechiladi

Endi har case — o'z qutisi, har qutida o'z xabar i.

5. switch (true) naqshi

switch faqat tenglikni tekshiradi. Oraliqlar-chi — masalan, "86 dan katta"? Buning uchun dasturchilar bir hiyla o'ylab topgan:

js
const ball = 78;
let baho;

switch (true) {
  case ball >= 86:
    baho = 5;
    break;
  case ball >= 71:
    baho = 4;
    break;
  case ball >= 56:
    baho = 3;
    break;
  default:
    baho = 2;
}

console.log(`Baho: ${baho}`); // Baho: 4

Qanday ishlaydi? Qavsda true turibdi. Har case dagi ifoda hisoblanadi: 78 >= 86 → false, 78 >= 71 → true. true === true — mos keldi! Ya'ni switch "qaysi shart rost?" deb qidiradi.

Lekin bu yerda xavfli tuzoq bor. case ifodasi aynan true bo'lishi kerak — truthy yetmaydi:

js
const promoKod = "BAHOR10";

switch (true) {
  case promoKod:
    console.log("Promo-kod bor");
    break;
  default:
    console.log("Promo-kod yo'q");
}

Konsolda:

text
Promo-kod yo'q

"BAHOR10" truthy, if (promoKod) da ishlagan bo'lardi. Lekin "BAHOR10" === true — false. Shuning uchun default ishladi. To'g'risi — case promoKod !== "": kabi aniq taqqoslash yozish.

Xulosa: switch (true) ishlaydi va eski kodlarda uchraydi. Lekin ko'p jamoalar uni yoqtirmaydi: else if zanjiri xuddi shu ishni tushunarliroq qiladi. Oraliqlar uchun else if ni tanlang.

6. switch ning muqobillari

6.1 Obyekt-lug'at: qiymatdan qiymatga

Ko'pincha switch faqat bitta ish qiladi: bir qiymatga qarab boshqa qiymatni tanlaydi. Masalan, choyxonada ichimlik nomiga qarab narx:

js
const ichimlik = "kofe";
let narx;

switch (ichimlik) {
  case "choy":
    narx = 3000;
    break;
  case "kofe":
    narx = 12000;
    break;
  case "sharbat":
    narx = 8000;
    break;
  default:
    narx = 0;
}

console.log(narx); // 12000

12 qator kod — uchta narx uchun. Bunday holatda dasturchilar ko'pincha obyekt ishlatadi. Obyekt (object) — "nom → qiymat" juftliklari to'plami. Xuddi choyxona devoridagi menyu taxtasi: chapda nom, o'ngda narx.

js
const narxlar = { choy: 3000, kofe: 12000, sharbat: 8000 };
const ichimlik = "kofe";

const narx = narxlar[ichimlik] ?? 0;
console.log(narx); // 12000

Uch qator! Nima bo'ldi:

  • { choy: 3000, ... } — menyu taxtasi. Har juftlik — nom: qiymat, vergul bilan ajratilgan.
  • narxlar[ichimlik] — "menyudan ichimlik dagi nomni top". ichimlik — "kofe", demak 12000.
  • Menyuda yo'q nom so'ralsa, natija undefined bo'ladi. ?? operatori uni 0 ga almashtiradi — bu default ning o'rnini bosadi.

Obyektlarni alohida darsda to'liq o'rganamiz. Hozircha shu shaklni tanib olsangiz yetarli.

Bo'sh joyni to'ldiring. Menyuda yo'q "kola" so'ralsa, narxlar["kola"] natijasi [:undefined], narxlar["kola"] ?? 0 natijasi esa [:0] bo'ladi.

Obyekt-lug'atning afzalligi: break unutish xavfi yo'q, yangi variant — bitta juftlik. Kamchiligi: u faqat qiymat tanlaydi. Har variantda turli amallar (bir necha qator kod) bajarilishi kerak bo'lsa — switch qulayroq.

6.2 Ternary zanjiri — ko'p variantda emas

Ternary darsida 3–4 variantli ternary zanjirini ko'rgan edik. 5–10 ta variantda u ko'zni charchatadigan uzun qatorlarga aylanadi. Bitta : adashsa — xatoni topish qiyin. Ko'p variant uchun switch yoki obyekt-lug'at tanlang.

6.3 Qaysi birini tanlash kerak?

Vaziyat Eng qulayi
Bitta qiymat, aniq variantlar, har birida turli amal switch
Bitta qiymat → boshqa qiymat (narx, nom, rang) Obyekt-lug'at
Oraliqlar (>=, <) yoki turli o'zgaruvchilar else if
Faqat 2 variant Ternary yoki if / else

Aslida switch bilan yozilgan har qanday kodni else if bilan ham yozish mumkin. Tanlov — qaysi biri o'qishga qulayroq ekanida.

7. Ko'p uchraydigan xatolar

7.1 break ni unutish

3.1-bo'limdagi "to'rt javob bergan bot". Har case oxirida break bor-yo'qligini tekshiring. Ataylab qo'ymagan bo'lsangiz — izoh yozing.

7.2 Satr va son

switch ("2") va case 2: — mos kelmaydi, chunki ===. Formadan kelgan qiymatni Number() bilan aylantiring yoki case larni satr qilib yozing.

7.3 case da || ishlatish

js
const kun = "yakshanba";

switch (kun) {
  case "shanba" || "yakshanba":
    console.log("Dam olish kuni");
    break;
  default:
    console.log("Ish kuni");
}

Konsolda:

text
Ish kuni

Yakshanba ish kuni bo'lib qoldi! "shanba" || "yakshanba" — bu bitta ifoda. Qisqa tutashuv qoidasi bo'yicha u birinchi truthy qiymatni, ya'ni "shanba" ni qaytaradi. Demak, bu case faqat "shanba" ga mos keladi. To'g'risi — 3.2-bo'limdagi guruhlash: case "shanba": va case "yakshanba": ni ketma-ket yozish.

7.4 Katta-kichik harf

"Fevral" va "fevral" — ikki xil satr. Foydalanuvchi qanday yozishini bilmaysiz. Shuning uchun qiymatni oldindan bir xil ko'rinishga keltiring: switch (oy.toLowerCase()). toLowerCase() — matnni o'zgartirish darsidan: hamma harfni kichik qiladi.

7.5 Ikki nuqta o'rniga nuqtali vergul

case "/start"; deb yozsangiz — SyntaxError: Unexpected token ';' ("kutilmagan belgi: ;"). case dan keyin doim : keladi.

8. Mashqlar

1-mashq (oson): Hafta kuni

kun o'zgaruvchisida 1 dan 7 gacha son bor. switch bilan uning nomini chiqaring: 1 — "Dushanba", 2 — "Seshanba" va shu tarzda 7 — "Yakshanba"gacha. Boshqa son bo'lsa — "Bunday kun yo'q". Kodni kun = 5 bilan sinang.

Yechim
js
const kun = 5;

switch (kun) {
  case 1:
    console.log("Dushanba");
    break;
  case 2:
    console.log("Seshanba");
    break;
  case 3:
    console.log("Chorshanba");
    break;
  case 4:
    console.log("Payshanba");
    break;
  case 5:
    console.log("Juma");
    break;
  case 6:
    console.log("Shanba");
    break;
  case 7:
    console.log("Yakshanba");
    break;
  default:
    console.log("Bunday kun yo'q");
}

Konsolda:

text
Juma

kun — son, case lar ham son. Turlar mos, === ishlaydi. kun = 9 bilan sinasangiz — default ishlaydi.

2-mashq (o'rta): Ish kuni yoki dam olish

Foydalanuvchi hafta kuni nomini yozdi: const kun = "Shanba"; (katta harf bilan). switch bilan quyidagini chiqaring:

  • dushanbadan jumagacha — "Ish kuni: 9:00 dan 18:00 gacha";
  • shanba va yakshanba — "Dam olish kuni";
  • boshqa matn — "Bunday kun yo'q".

Ishora: katta-kichik harf muammosini toLowerCase() bilan hal qiling (7.4-bo'lim), bir xil natijali kunlarni guruhlang (3.2-bo'lim).

Yechim
js
const kun = "Shanba";

switch (kun.toLowerCase()) {
  case "dushanba":
  case "seshanba":
  case "chorshanba":
  case "payshanba":
  case "juma":
    console.log("Ish kuni: 9:00 dan 18:00 gacha");
    break;
  case "shanba":
  case "yakshanba":
    console.log("Dam olish kuni");
    break;
  default:
    console.log("Bunday kun yo'q");
}

Konsolda:

text
Dam olish kuni

"Shanba".toLowerCase() — "shanba". Shuning uchun case "shanba": mos keldi. toLowerCase() bo'lmaganda "Shanba" === "shanba" — false bo'lardi va default ishlagan bo'lardi.

3-mashq (qiyin): switch dan obyekt-lug'atga

Valyuta ayirboshlash shoxobchasida kurslar (misol uchun olingan) switch bilan yozilgan:

js
const valyuta = "EUR";
const summa = 100;
let kurs;

switch (valyuta) {
  case "USD":
    kurs = 12800;
    break;
  case "EUR":
    kurs = 14000;
    break;
  case "RUB":
    kurs = 150;
    break;
  default:
    kurs = 0;
}

console.log(`${summa} ${valyuta} = ${summa * kurs} so'm`);
  1. Kodni ishga tushiring va natijani yozib oling.
  2. Xuddi shu mantiqni obyekt-lug'at va ?? bilan qayta yozing (6.1-bo'lim). Natija o'zgarmasin.
  3. Yangi valyuta — KZT (kursi 25) — qo'shing. Ikkala variantda nechta qator qo'shish kerak bo'lganini solishtiring.
Yechim

1-qadamda natija: 100 EUR = 1400000 so'm.

js
const kurslar = { USD: 12800, EUR: 14000, RUB: 150, KZT: 25 };
const valyuta = "EUR";
const summa = 100;

const kurs = kurslar[valyuta] ?? 0;
console.log(`${summa} ${valyuta} = ${summa * kurs} so'm`);
// 100 EUR = 1400000 so'm

Obyektda KZT: 25 — bitta juftlik qo'shildi, xolos. switch da esa 3 qator kerak edi: case "KZT":, kurs = 25; va break;. break ni unutish xavfi ham yo'q. Noma'lum valyutada ("GBP") kurslar["GBP"] — undefined, ?? uni 0 ga almashtiradi — xuddi default dagidek.

9. Real ishda

  • Telegram botlar: buyruqlarni (/start, /help) tanlash ko'pincha switch yoki obyekt-lug'at bilan yoziladi.
  • Holat bilan ishlash: buyurtma holati — "yangi", "yo'lda", "yetkazildi", "bekor". Har holatda boshqa amal — klassik switch.
  • Redux va useReducer (React'da ma'lumotni boshqarish usullari, kursda alohida o'rganamiz): ular ichida switch eng mashhur naqsh.
  • Kod sifati: ESLint'da default-case (default ni unutmaslik) va no-fallthrough (izohsiz oqib o'tish yo'q) qoidalari bor.

Intervyuda ko'pincha shunday kod beriladi va "konsolda nima chiqadi?" deb so'raladi. Bunda break qo'yilmagan case bo'ladi. Endi siz uni bir qarashda topasiz.

Xulosa

  • switch bitta qiymatni ko'p case bilan === orqali solishtiradi — tur ham mos bo'lishi kerak.
  • Mos case dan keyin kod break gacha bajariladi. break bo'lmasa — keyingi case larga oqib o'tadi.
  • Bo'sh case larni ketma-ket yozib, bir nechta variantni guruhlash mumkin. Ataylab oqib o'tishga izoh yozing.
  • default — hech biri mos kelmaganda. Uni oxirida va doim yozgan ma'qul.
  • case ichida let kerak bo'lsa — case ni { } ga oling.
  • Qiymat → qiymat uchun obyekt-lug'at qisqaroq, oraliqlar uchun else if aniqroq. switch (true) ishlaydi, lekin truthy'ni emas, faqat true ni tutadi.

Keyingi dars: for sikli — bir xil ishni kerakli marta takrorlashni o'rganamiz.

Ulashish:Telegram'da

Izohlar (0)

Izoh yozish uchun kiring.

  • Hozircha izoh yo'q. Birinchi bo'ling!
JavaScript switch: bitta qiymatni ko'p variant bilan solishtirish — IlmHamroh