Mundarija (34)
- Bu darsda
- 1. Nega bu kerak?
- 2. Tur pozitsiyasidagi typeof
- 2.1 Ikki xil typeof
- 2.2 Qiymat va tur — ikki alohida dunyo
- 2.3 as const bilan — literal turlar
- 2.4 Funksiyaning typeof i
- 3. keyof typeof: qiymatdan kalitlar
- 3.1 Juftlik
- 3.2 Index signature'da keyof
- 4. Indexed access: T["kalit"]
- 4.1 Bitta maydonning turi
- 4.2 Union kalit va T[keyof T]
- 4.3 Xatolar
- 4.4 Ichma-ich: Order["items"][number]
- 5. (typeof SIZES)[number]: massivdan union
- 5.1 Ro'yxat — bitta manba
- 5.2 Obyekt qiymatlaridan union
- 5.3 Qavslar
- 6. TypeScript ushlamaydigan tuzoq: any dan chiqarilgan tur
- 6.1 Qachon chiqarish, qachon qo'lda yozish?
- 7. Ko'p uchraydigan xatolar
- 7.1 Tur va qiymatni almashtirish
- 7.2 Indexed access'da qiymat
- 7.3 as const siz [number]
- 7.4 Qiymat va turni alohida yozish
- 7.5 any dan tur chiqarish
- 8. Mashqlar
- 1-mashq (oson): Turlarni chiqaring
- 2-mashq (o'rta): Javob turidan qismlar
- 3-mashq (qiyin): Amaliy tajriba — menyudan turlar
- 9. Real ishda
- Xulosa
- Manbalar
TypeScript keyof, typeof va indexed access: turlarni qiymatlardan chiqarish
Qisqacha: Turni qo'lda takrorlash o'rniga uni mavjud qiymat yoki turdan chiqarib olish mumkin.
typeof MENU— o'zgaruvchining turi,keyof typeof MENU— uning kalitlari ("osh" | "manti"),Dish["price"]— bitta maydon turi,(typeof SIZES)[number]— massiv elementlari union'i. Qiymat o'zgarsa, tur ham o'zi o'zgaradi.
Bu darsda
- Tur pozitsiyasidagi
typeofni JavaScript'ningtypeofoperatoridan farqlaysiz. keyofni qiymatdan olingan turlar bilan birga ishlatasiz.- Indexed access (
T["price"],T[K], ichma-ichT["items"][number]) bilan maydon turlarini olasiz. as constmassiv va obyektdan union yasaysiz — "bitta haqiqat manbai".anyqiymatdan tur chiqarish tuzog'ini taniysiz.
Oldin bilishingiz kerak: Function overload va this turi, Generic cheklovlar va keyof, enum va uning muqobillari, Massiv va tuple turlari.
1. Nega bu kerak?
O'tgan darslarda turlarni qo'lda yozdik. Lekin ko'pincha qiymat allaqachon bor va tur uni takrorlaydi. «Bahor» menyusi:
const MENU = {
osh: { price: 35000, cookMinutes: 40 },
manti: { price: 30000, cookMinutes: 45 },
somsa: { price: 8000, cookMinutes: 30 },
};
type DishName = "osh" | "manti";
function priceOf(name: DishName): number {
return MENU[name].price;
}
console.log(priceOf("osh")); // 35000Jasur aka menyuga somsa qo'shdi, Sardor MENU ga yozdi — lekin DishName ni unutdi. tsc jim: priceOf("somsa") chaqirilmaguncha hech narsa demaydi, chaqirilsa esa "somsa — DishName emas" deydi, garchi somsa menyuda bo'lsa ham. Bir ma'lumot ikki joyda yozilgan — ular albatta ajralib qoladi.
Yechim — turni qiymatdan chiqarib olish: type DishName = keyof typeof MENU. Menyu o'zgarsa — tur o'zi o'zgaradi. Dasturchilar buni "bitta haqiqat manbai" (single source of truth) deyishadi.
2. Tur pozitsiyasidagi typeof
2.1 Ikki xil typeof
JavaScript'da typeof — ishlash paytidagi operator, u satr qaytaradi (typeof va turni to'g'ri aniqlash darsi):
const config = { serviceRate: 0.1, currency: "so'm" };
console.log(typeof config); // objectTypeScript'da esa typeof tur yozilgan joyda ham ishlatiladi — u o'zgaruvchining TypeScript turini beradi:
const config = { serviceRate: 0.1, currency: "so'm" };
type Config = typeof config;
const test: Config = { serviceRate: 0.15, currency: "so'm" };
console.log(test.serviceRate); // 0.15type Config = typeof config — { serviceRate: number; currency: string }. Bir so'z, ikki ma'no: qiymat yozilgan joyda (console.log(typeof x)) — JavaScript operatori, tur yozilgan joyda (type X = typeof x, : typeof x) — TypeScript operatori. Ikkinchisi JavaScript'da butunlay o'chadi.
2.2 Qiymat va tur — ikki alohida dunyo
TypeScript qiymatlar va turlarni alohida saqlaydi. Birini ikkinchisining o'rnida ishlatsangiz:
type Dish = { name: string; price: number };
const d = typeof Dish;
const config = { serviceRate: 0.1 };
let c: config;Kompilyator:
TS2693: 'Dish' only refers to a type, but is being used as a value here.
TS2749: 'config' refers to a value, but is being used as a type here. Did you mean 'typeof config'?TS2693: "Dishfaqat tur, lekin qiymat sifatida ishlatildi". JavaScript'daDishdegan narsa yo'q — u o'chirilgan.TS2749: "config— qiymat, lekin tur sifatida ishlatildi.typeof configdemoqchimidingiz?" TypeScript tuzatishni ham taklif qildi.
Klass ikkala dunyoda bor: class Order ham qiymat (konstruktor), ham tur (nusxa shakli). Shuning uchun let o: Order va new Order() ikkalasi ham ishlaydi (Klasslar TypeScript'da).
2.3 as const bilan — literal turlar
typeof qiymatning chiqarilgan turini beradi. Obyekt maydonlari kengaygan bo'ladi (Tur chiqarish):
| Qiymat | typeof natijasi |
|---|---|
{ serviceRate: 0.1, currency: "so'm" } |
{ serviceRate: number; currency: string } |
{ … } as const |
{ readonly serviceRate: 0.1; readonly currency: "so'm" } |
Aniq qiymatlar kerak bo'lsa (holatlar, o'lchamlar) — as const. Faqat shakl kerak bo'lsa (sozlama) — oddiy obyekt.
2.4 Funksiyaning typeof i
typeof funksiyaga qo'llansa — uning to'liq imzosini beradi. Bu callback parametrlarini yozishda qulay: imzo qo'lda takrorlanmaydi.
function priceWithService(price: number, rate = 0.1): number {
return Math.round(price * (1 + rate));
}
type PriceFn = typeof priceWithService;
function applyToAll(prices: readonly number[], fn: PriceFn) {
return prices.map((p) => fn(p));
}
const result = applyToAll([35000, 5000], priceWithService);
console.log(result); // [ 38500, 5500 ]PriceFn — (price: number, rate?: number) => number. Standart qiymatli rate turda ixtiyoriy parametr bo'lib qoldi. Endi boshqa narx funksiyasi ham shu "qolip"ga tekshiriladi:
function priceWithService(price: number, rate = 0.1): number {
return Math.round(price * (1 + rate));
}
const wrong: typeof priceWithService = (p: string) => p.length;Kompilyator:
TS2322: Type '(p: string) => number' is not assignable to type '(price: number, rate?: number) => number'.
Types of parameters 'p' and 'price' are incompatible.
Type 'number' is not assignable to type 'string'.Tarjimasi: "(p: string) => number turini (price: number, rate?: number) => number turiga berib bo'lmaydi". Zanjirni pastdan o'qing: "parametrlar mos emas — number ni string ga berib bo'lmaydi". Funksiya turlari mosligi qoidasi — Funksiyalarni tiplash darsida. typeof fn ning eng mashhur qo'llanishi esa keyingi darsda: ReturnType<typeof fn> — "shu funksiya qaytaradigan tur".
Tekshirib ko'ring:
let count = 5; type C = typeof count;vaconst count = 5; type C = typeof count;—Cqanday tur?
Javob
Birinchisida number — let kengaygan turni oladi. Ikkinchisida 5 — const literal tur. typeof o'zgaruvchiga TypeScript bergan turni oladi, uning ichidagi qiymatni emas.
3. keyof typeof: qiymatdan kalitlar
3.1 Juftlik
Generic cheklovlar va keyof darsida keyof turdan kalitlar union'ini olardi. Qiymatdan olish uchun ikkalasi birga ishlatiladi:
const MENU = {
osh: { price: 35000, cookMinutes: 40 },
manti: { price: 30000, cookMinutes: 45 },
somsa: { price: 8000, cookMinutes: 30 },
};
type DishName = keyof typeof MENU;
function priceOf(name: DishName): number {
return MENU[name].price;
}
console.log(priceOf("somsa")); // 8000O'ngdan chapga o'qing: typeof MENU — menyu obyektining turi, keyof — uning kalitlari: "osh" | "manti" | "somsa". Endi menyuga taom qo'shilsa, DishName o'zi kengayadi. Olib tashlansa — eski nomni ishlatgan har bir joy tsc xatosi beradi.
Qavslarga e'tibor bering: keyof typeof MENU qavssiz to'g'ri o'qiladi — keyof (typeof MENU). enum muqobillari darsidagi (typeof X)[keyof typeof X] qolipining ikkinchi yarmi — aynan shu.
3.2 Index signature'da keyof
Kalitlari noma'lum lug'atda keyof aniq ro'yxat bera olmaydi:
| Tur | keyof |
|---|---|
{ osh: number; manti: number } |
"osh" | "manti" |
{ [k: string]: number } |
string | number |
{ [n: number]: string } |
number |
Ikkinchi qatordagi number ajablanarli ko'rinadi. Sababi Index signature va Record darsida: JavaScript son kalitni satrga aylantiradi (obj[1] = obj["1"]), shuning uchun satr imzosi son bilan murojaatga ham ruxsat beradi.
4. Indexed access: T["kalit"]
4.1 Bitta maydonning turi
Obyekt turidan bitta maydonning turini olish — qiymatlardagi obj["price"] ning tur darajasidagi aksi:
type Dish = { name: string; price: number; cookMinutes: number };
type Price = Dish["price"];
const lagmon: Price = 28000;
console.log(lagmon); // 28000Dish["price"] — indexed access type (indeks bo'yicha tur): number. Nega number deb yozmaslik kerak? Ertaga narxlar bigint yoki { amount: number; currency: string } bo'lsa, Dish["price"] ishlatilgan hamma joy avtomatik yangilanadi.
vazifalar da aynan shunday qator bor (paket.ts):
const PAKET_VERSIYASI: Paket["versiya"] = 1;Paket turida versiya: 1 (literal tur). PAKET_VERSIYASI uning turini oladi — tur o'zgarsa (versiya: 2), bu qator TS2322 bilan "qiymatni ham yangilang" deydi. 12-qismda JSDoc'da /** @type {Paket["versiya"]} */ deb yozilgan edi — sintaksis bir xil.
4.2 Union kalit va T[keyof T]
Kalit o'rnida union ham bo'lishi mumkin — natija ham union bo'ladi:
| Yozuv | Natija |
|---|---|
Dish["name"] |
string |
Dish["name" | "price"] |
string | number |
Dish[keyof Dish] |
string | number — hamma qiymatlar turi |
T[keyof T] — "T ning qiymatlari union'i". Bu (typeof X)[keyof typeof X] qolipining umumiy shakli.
4.3 Xatolar
type Dish = { name: string; price: number };
type P = Dish["narx"];
const key = "price";
type Q = Dish[key];Kompilyator:
TS2339: Property 'narx' does not exist on type 'Dish'.
TS2538: Type 'key' cannot be used as an index type.
TS2749: 'key' refers to a value, but is being used as a type here. Did you mean 'typeof key'?TS2339— "Dishturidanarxxususiyati yo'q". Oddiy: bunday maydon yo'q.TS2538— "keyni indeks turi sifatida ishlatib bo'lmaydi",TS2749— "keyqiymat, lekin tur o'rnida ishlatildi". Ikkalasi bitta xato: kvadrat qavs ichida tur kerak,keyesa qiymat. Tuzatish —Dish[typeof key]:key—const, uning turi"price", natija —number.
4.4 Ichma-ich: Order["items"][number]
Indexed access zanjir bo'lib ham yoziladi. Massiv elementining turi uchun maxsus kalit — number:
type Order = {
id: number;
items: { dish: string; qty: number }[];
};
type Item = Order["items"][number];
type ItemDish = Order["items"][number]["dish"];
const line: Item = { dish: "Osh", qty: 2 };
const name: ItemDish = "Manti";
console.log(line.qty, name); // 2 MantiKompilyator zanjirni chapdan o'ngga, bir bo'g'indan hisoblaydi:
| Qadam | Nima bo'ldi? | Natija |
|---|---|---|
| 1 | Order["items"] — items maydonining turi |
{ dish: string; qty: number }[] |
| 2 | [number] — istalgan raqamli indeksdagi element |
{ dish: string; qty: number } |
| 3 | ["dish"] — elementning dish maydoni |
string |
Bu turni server javobidan olinganda ayniqsa foydali: katta javob turi bir marta yoziladi, qismlari esa undan "kesib" olinadi.
Bu chiqarishni chizmada ko'ramiz:
flowchart LR
A["const MENU = {…}"] -- "typeof" --> B["typeof MENU"]
B -- "keyof" --> C["DishName<br/>'osh' | 'manti' | …"]
B -- "[DishName]" --> D["MenuEntry<br/>{ price; cookMinutes }"]
D -- "['price']" --> E["number"]Chap tomonda — bitta qiymat. Qolgan hamma turlar undan chiqarilgan, hech biri qo'lda takrorlanmagan.
Tekshirib ko'ring:
type Guest = { name: string; phones: string[] }uchunGuest["phones"][number]vaGuest["phones"]turlari qanday?
Javob
Guest["phones"] — string[] (massiv), Guest["phones"][number] — string (bitta element). [number] "massivdan bitta elementga tushish" degani.
5. (typeof SIZES)[number]: massivdan union
5.1 Ro'yxat — bitta manba
enum va uning muqobillari darsida bu qolipni ko'rgandik, endi uni qismlarga ajrata olasiz:
const SIZES = ["kichik", "o'rta", "katta"] as const;
type Size = (typeof SIZES)[number];
function isSize(text: string): text is Size {
return SIZES.some((s) => s === text);
}
console.log(isSize("katta"), isSize("XL")); // true falsetypeof SIZES—readonly ["kichik", "o'rta", "katta"](as consttufayli tuple).[number]— istalgan indeksdagi element:"kichik" | "o'rta" | "katta".
Aniq indeks ham mumkin: (typeof SIZES)[0] — "kichik". as const siz esa typeof SIZES — string[], [number] — oddiy string: union yo'qoladi.
const SIZES = ["kichik", "o'rta", "katta"] as const;
const s: (typeof SIZES)[number] = "XL";Kompilyator:
TS2322: Type '"XL"' is not assignable to type '"katta" | "kichik" | "o'rta"'.Tarjimasi: ""XL" turini uch o'lcham union'iga berib bo'lmaydi". Union a'zolari xabarda alifbo tartibida — ma'nosi o'sha.
5.2 Obyekt qiymatlaridan union
Massivda [number] bo'lsa, as const obyektda qiymatlar union'i [keyof typeof X] bilan olinadi. Ikkalasini yonma-yon qo'yamiz:
| Manba | Qolip | Natija |
|---|---|---|
["S", "M"] as const |
(typeof X)[number] |
"S" | "M" |
{ Small: "S", Medium: "M" } as const |
(typeof X)[keyof typeof X] |
"S" | "M" |
{ Small: "S", Medium: "M" } as const |
keyof typeof X |
"Small" | "Medium" |
Ro'yxat kerak bo'lsa (tugmalar, <select>) — massiv. Nom bilan murojaat kerak bo'lsa (SIZE.Small, enum o'rnida) — obyekt. Ikkala holatda ham tur qiymatdan chiqariladi va qo'lda takrorlanmaydi.
Tekshirib ko'ring:
const ROLES = ["egasi", "oshpaz", "ofitsiant"] as const;—(typeof ROLES)[number]va(typeof ROLES)["length"]turlari qanday?
Javob
(typeof ROLES)[number] — "egasi" | "oshpaz" | "ofitsiant". (typeof ROLES)["length"] — 3: tuple uzunligi literal tur, length ham oddiy maydon kabi indexed access bilan olinadi.
5.3 Qavslar
typeof SIZES[number] (qavssiz) ham ishlaydi — TypeScript uni (typeof SIZES)[number] deb o'qiydi. Lekin o'quvchi uchun noaniq: "SIZES[number] ning turimi?" Shuning uchun Prettier va ko'p jamoalar qavsni yozadi. Biz ham shunday yozamiz.
6. TypeScript ushlamaydigan tuzoq: any dan chiqarilgan tur
Tur chiqarish qiymat qanday bo'lsa, shunday tur beradi. Qiymat any bo'lsa-chi?
const sample = JSON.parse('{"total": 63000}');
type Order = typeof sample;
const order: Order = { totl: 1 };
console.log(order.total.toFixed(0));tsc — xatosiz. Node esa:
TypeError: Cannot read properties of undefined (reading 'toFixed')JSON.parse any qaytaradi, demak typeof sample — any, Order ham any. { totl: 1 } (harf xatosi) jim qabul qilindi, order.total ham tekshirilmadi. "Namuna JSON'dan tur yasab olish" g'oyasi shu yerda buziladi: typeof ishlash paytidagi namunani emas, tsc bilgan turni oladi.
Qoida: typeof ni faqat turi aniq qiymatlarga qo'llang — o'zingiz yozgan konstantalar, as const ro'yxatlar, sozlamalar. Tashqi ma'lumot (JSON, server, localStorage) uchun turni qo'lda yozing va ishlash paytida tekshiring (API ma'lumotlarini tiplash).
6.1 Qachon chiqarish, qachon qo'lda yozish?
Tur chiqarish kuchli, lekin har doim ham to'g'ri yo'l emas. Asosiy savol: haqiqat manbai qayerda?
- Manba — kodning o'zidagi qiymat (menyu konstantasi, holatlar ro'yxati, sozlama). Unda turni qiymatdan chiqaring:
keyof typeof MENU,(typeof SIZES)[number]. Qiymat va tur ajralib qolmaydi. - Manba — tashqi kelishuv (server javobi, fayl formati, boshqa jamoa API'si). Unda tur — hujjat: uni qo'lda yozing (yoki API sxemasidan avtomatik yarating), qiymat esa ishlash paytida shu turga tekshirilsin. Namuna qiymatdan chiqarilgan tur faqat bitta misolni aks ettiradi — ixtiyoriy maydonlar,
nullbo'lishi mumkin bo'lgan joylar unda ko'rinmaydi. - Manba — boshqa tur. Unda qismlarni indexed access bilan oling (
Order["items"][number]), butun turni esa bir joyda saqlang.
vazifalar ham shu qoidaga amal qiladi: VazifaMalumoti (JSON shakli) — turlar.ts da qo'lda yozilgan tur, chunki u eksport fayli va server bilan kelishuv. PAKET_VERSIYASI esa shu turdan chiqarilgan (Paket["versiya"]).
7. Ko'p uchraydigan xatolar
7.1 Tur va qiymatni almashtirish
typeof Dish (tur ustida) — TS2693; let c: config (qiymat tur o'rnida) — TS2749. Tuzatish: qiymatdan tur — typeof config; turdan qiymat olib bo'lmaydi.
7.2 Indexed access'da qiymat
Dish[key] — TS2538/TS2749. Tuzatish: Dish[typeof key] yoki Dish["price"].
7.3 as const siz [number]
(typeof SIZES)[number] — string, union yo'q. Tuzatish: massiv oxirida as const.
7.4 Qiymat va turni alohida yozish
MENU va type DishName = "osh" | … — ajralib qoladi. Tuzatish: keyof typeof MENU.
7.5 any dan tur chiqarish
typeof JSON.parse(…) — any. Tuzatish: tashqi ma'lumot turini qo'lda yozing.
8. Mashqlar
1-mashq (oson): Turlarni chiqaring
const TABLES = { window: 4, corner: 2, hall: 8 } as const;
type TableName = keyof typeof TABLES;
type Seats = (typeof TABLES)[TableName];
const t: TableName = "corner";
console.log(TABLES[t]); // 2TableName da nechta a'zo bor: [:3]. (typeof TABLES)["hall"] turi (literal son): [:8]. as const siz Seats turi: .
Yechim
- 3 ta:
"window" | "corner" | "hall". 8:as constqiymatlarni literal qildi.number:as constsiz hamma maydonlarnumberga kengayadi, ularning union'i hamnumber.
2-mashq (o'rta): Javob turidan qismlar
Server javobining turi bitta katta tur sifatida berilgan. Undan uchta kichik turni qo'lda yozmasdan, indexed access bilan oling: bitta buyurtma (OrderRow), bitta qator (LineRow) va to'lov usuli (PayMethod).
type DayReport = {
date: string;
orders: {
id: number;
lines: { dish: string; qty: number }[];
pay: "naqd" | "karta";
}[];
};Yechim
type DayReport = {
date: string;
orders: {
id: number;
lines: { dish: string; qty: number }[];
pay: "naqd" | "karta";
}[];
};
type OrderRow = DayReport["orders"][number];
type LineRow = OrderRow["lines"][number];
type PayMethod = OrderRow["pay"];
const line: LineRow = { dish: "Osh", qty: 2 };
const pay: PayMethod = "karta";
const row: OrderRow = { id: 7, lines: [line], pay };
console.log(row.lines.length, row.pay); // 1 kartaOrderRow— massiv elementi ([number]),LineRow— undan ham bir qavat ichkari.PayMethod—"naqd" | "karta": literal union to'liq saqlandi.- Server javobi o'zgarsa (masalan,
payga"click"qo'shilsa), uchala tur ham avtomatik yangilanadi.
3-mashq (qiyin): Amaliy tajriba — menyudan turlar
Mashq kurs/mashqlar/15/ papkasida. 25-qiymatdan-tur/menu.ts ni avval qo'lda yozilgan tur bilan yarating: MENU obyektida osh, manti, lag'mon va somsa (narx va pishish vaqti), type DishName = "osh" | "manti" | "lagmon" (somsa — "unutilgan") va priceOf(name: DishName). Testda priceOf("somsa") ni chaqiring. npx tsc --pretty false nima deydi?
Keyin hamma turlarni qiymatlardan chiqaring:
DishName—keyof typeof MENU,MenuEntry—(typeof MENU)[DishName],priceOfnatijasi —MenuEntry["price"].SIZES = ["kichik", "o'rta", "katta"] as constvaSize— undan.parseSize(text)— matndanSize(noma'lum bo'lsaTypeError);portionPrice(name, size)— kichik ×0.75, o'rta ×1, katta ×1.5, butun so'mgacha.
Yechim
Qo'lda yozilgan turda tsc 7.0.2 testni to'xtatdi:
25-qiymatdan-tur/menu.test.ts(7,24): error TS2345: Argument of type '"somsa"' is not assignable to parameter of type 'DishName'.Somsa menyuda bor, lekin turda yo'q — «Nega bu kerak?» bo'limidagi ajralish.
// 25-qiymatdan-tur/menu.ts — turlar qiymatlardan chiqariladi
export const MENU = {
osh: { price: 35000, cookMinutes: 40 },
manti: { price: 30000, cookMinutes: 45 },
lagmon: { price: 28000, cookMinutes: 25 },
somsa: { price: 8000, cookMinutes: 30 },
};
// Menyuga taom qo'shilsa — bu tur o'zi kengayadi
export type DishName = keyof typeof MENU;
export type MenuEntry = (typeof MENU)[DishName];
export const SIZES = ["kichik", "o'rta", "katta"] as const;
export type Size = (typeof SIZES)[number];
const SIZE_FACTORS: Record<Size, number> = {
kichik: 0.75,
"o'rta": 1,
katta: 1.5,
};
export function priceOf(name: DishName): MenuEntry["price"] {
return MENU[name].price;
}
export function parseSize(text: string): Size {
const found = SIZES.find((s) => s === text);
if (found === undefined) {
throw new TypeError(`Noma'lum o'lcham: ${text}`);
}
return found;
}
export function portionPrice(name: DishName, size: Size): number {
return Math.round(priceOf(name) * SIZE_FACTORS[size]);
}// 25-qiymatdan-tur/menu.test.ts
import { test } from "node:test";
import assert from "node:assert/strict";
import { MENU, priceOf, parseSize, portionPrice } from "./menu.ts";
test("priceOf: menyudagi har taom", () => {
assert.equal(priceOf("somsa"), 8000);
assert.equal(Object.keys(MENU).length, 4);
});
test("parseSize: matndan o'lcham", () => {
assert.equal(parseSize("katta"), "katta");
assert.throws(() => parseSize("XL"), TypeError);
});
test("portionPrice: o'lcham koeffitsiyenti bilan", () => {
assert.equal(portionPrice("osh", "katta"), 52500);
assert.equal(portionPrice("somsa", "kichik"), 6000);
});MENUdaas constyo'q — bizga taom nomlari (kalitlar) aniq kerak, narxlar esanumberbo'lishi yetarli. Kalitlaras constsiz ham aniq:keyofobyekt kalitlarini kengaytirmaydi.SIZE_FACTORS: Record<Size, number>— o'lcham qo'shilsa, koeffitsiyentni unutib bo'lmaydi (Index signature vaRecord).MENU[name]—name: DishNamebo'lgani uchunnoUncheckedIndexedAccessbilan hamundefinedemas.- 35 000 × 1.5 = 52 500, 8 000 × 0.75 = 6 000.
npx tsc --pretty false — chiqishsiz. node --test 25-qiymatdan-tur/menu.test.ts bizda (Node 24.21.0) shunday chiqdi:
✔ priceOf: menyudagi har taom (1.9094ms)
✔ parseSize: matndan o'lcham (1.2068ms)
✔ portionPrice: o'lcham koeffitsiyenti bilan (0.5316ms)
ℹ tests 3
ℹ suites 0
ℹ pass 3
ℹ fail 0
ℹ cancelled 0
ℹ skipped 0
ℹ todo 0
ℹ duration_ms 294.4935XATOLAR.md ga qo'shing: TS2693, TS2749, TS2538. Keyin kurs/mashqlar papkasidan:
git add 15/25-qiymatdan-tur 15/XATOLAR.md
git commit -m "15/25: menu.ts — keyof typeof va indexed access"9. Real ishda
- Konstantalardan turlar: marshrutlar ro'yxati, ruxsatlar, til kodlari, holatlar —
as const+(typeof X)[number]yokikeyof typeof X. Kutubxonalar va katta loyihalarda eng ko'p uchraydigan qoliplardan. - Katta javob turlaridan qismlar:
Response["data"]["items"][number]— server turi bir marta (ko'pincha avtomatik) yaratiladi, komponentlar undan kerakli qismini oladi. vazifalarda:Paket["versiya"],Metric["rating"](olchov.ts:Readonly<Record<Metric["rating"], string>>— web-vitals kutubxonasidagi baho turlaridan matnlar jadvali).- Keyingi qadam:
ReturnType<typeof fn>— funksiya natijasidan tur (Utility types).typeofshu yerda ham asosiy rol o'ynaydi. - Intervyu: "
typeofTypeScript'da nima qiladi?", "keyof typeof objnima?", "Massivdan union qanday olinadi?" — juda tez-tez beriladi.
Xulosa
- Tur pozitsiyasidagi
typeof x— o'zgaruvchining TypeScript turi; JavaScript'dagitypeof(satr qaytaradi) bilan aralashtirmang. - Qiymat va tur — alohida dunyolar:
TS2693(tur qiymat o'rnida),TS2749(qiymat tur o'rnida, "Did you mean 'typeof …'"). keyof typeof OBJ— qiymatdagi kalitlar union'i. Indexed accessT["k"],T[K],T[keyof T]— maydon turlari.[number]— massiv elementi:Order["items"][number],(typeof SIZES)[number](as constbilan — union).- Tur faqat
tscbilgan darajada aniq:anyqiymatdan chiqarilgan tur hamany.
Keyingi dars: Utility types — Partial, Pick, Omit, Record, ReturnType va boshqa tayyor tur-funksiyalar; vazifalar dagi api.ts ular bilan .ts ga o'tadi.
Manbalar
- TypeScript Handbook: "Typeof Type Operator" — typescriptlang.org/docs/handbook/2/typeof-types.html
- TypeScript Handbook: "Keyof Type Operator" — typescriptlang.org/docs/handbook/2/keyof-types.html
- TypeScript Handbook: "Indexed Access Types" — typescriptlang.org/docs/handbook/2/indexed-access-types.html
Izohlar (0)
Izoh yozish uchun kiring.
- Hozircha izoh yo'q. Birinchi bo'ling!