Mundarija (22)
- 1. Kirish va motivatsiya
- 2. Nazariya — chuqur tushuntirish
- 2.1. Nega xotira muhim
- 2.2. Generatorlar (oqim)
- 2.3. Xotira o'lchash
- 2.4. __slots__ (ixcham obyekt)
- 2.5. Ma'lumot tuzilmalari
- 2.6. Xotira oqishi (memory leak)
- 2.7. Xotira optimizatsiyasi amaliyoti
- 2.8. Xotira — vaqt bilan muvozanat
- 3. Tez ma'lumotnoma
- 4. Batafsil misollar
- Misol 1 — Generator vs ro'yxat (xotira)
- Misol 2 — slots (ixcham obyekt)
- Misol 3 — Ma'lumot tuzilmalari (xotira)
- Misol 4 — Xotira oqishi (memory leak)
- 5. To'g'ri va noto'g'ri tushunishlar
- 6. Keng tarqalgan xatolar va yechimlari
- 7. Integratsiya — bu bilim qayerda kerak bo'ladi
- 8. Eng yaxshi amaliyotlar
- 9. Amaliy topshiriq
- Xulosa
29.9-dars: Xotira optimizatsiyasi
29-QISM — MIQYOS VA UNUMDORLIK · 9-dars
1. Kirish va motivatsiya
Unumdorlik faqat tezlik emas — xotira ham muhim resurs. Xotira tugasa, dastur yiqiladi (out of memory) yoki sekinlashadi (svop — diskka ko'chirish). Katta ma'lumot bilan ishlaganda (million qator, katta fayl) butun ma'lumotni xotiraga yuklash — halokat (10 GB fayl 8 GB xotiraga sig'maydi). Yoki dastur asta-sekin xotira yeydi (memory leak) — soatlar davomida yiqiladi. Xotira optimizatsiyasi — dastur xotira sarfini kamaytirish: ma'lumotni oqim (stream) sifatida qayta ishlash (generatorlar), obyektlarni ixcham qilish (__slots__), to'g'ri ma'lumot tuzilmalari, xotira oqishlarini oldini olish. Xotira — tezlik kabi optimallashtiriladigan resurs.
Xotira optimizatsiyasi — dastur xotira sarfini kamaytirish usullari: xotira o'lchash (sys.getsizeof, tracemalloc — 29.2), generatorlar (13-qism — oqim, butun ma'lumotni yuklamaslik), __slots__ (obyekt xotirasini kamaytirish), ma'lumot tuzilmalari (to'g'ri tanlash — list vs set vs array), xotira oqishi (memory leak — keraksiz havolalar), time-space tradeoff (29.3 — vaqt vs xotira). Prinsip: katta ma'lumot — oqim, xotira o'lchash, ixcham obyekt. Bu profiling (29.2 — xotira profiling), kesh (29.3 — xotira narxi) bilan bog'liq. Xotira optimizatsiyasi — xotira-samarali kod. Kam xotira — barqaror tizim.
Real vaziyat. Bir dastur 5 GB CSV faylni qayta ishlardi — butun faylni ro'yxatga yuklardi (list(reader)) — xotira tugab yiqilardi (out of memory). Xotira optimizatsiyasi: fayl generator bilan qator-qator o'qildi (for row in reader — butun yuklamasdan), obyektlar __slots__ bilan ixcham qilindi. Endi dastur 5 GB faylni 100 MB xotirada qayta ishladi (oqim — bir vaqtda bir qator). Xotira optimizatsiyasi — katta ma'lumotni kichik xotirada.
Bu darsda xotira optimizatsiyasini o'rganamiz.
Bu darsda:
- Nega xotira muhim
- Generatorlar (oqim)
- Xotira o'lchash
__slots__(ixcham obyekt)- Ma'lumot tuzilmalari
- Xotira oqishi (memory leak)
- Xotira optimizatsiyasi amaliyoti
- Amaliy: xotira modeli
ℹ Misollar sof Python (
sys.getsizeof, generatorlar) bilan xotira mantiqini ko'rsatadi (deterministik).
2. Nazariya — chuqur tushuntirish
2.1. Nega xotira muhim
Cheklangan resurs:
Xotira cheklangan (masalan 8 GB):
tugasa → dastur yiqiladi (out of memory)
yoki svop (diskka — sekin)
katta ma'lumot: butun yuklash → halokat
10 GB fayl → 8 GB xotira (sig'maydi!)Nega xotira — xotira cheklangan resurs (server 8 GB, 16 GB): tugasa dastur yiqiladi (out of memory — OOM) yoki sekinlashadi (svop — diskka ko'chirish, sekin). Sabab: katta ma'lumot (million qator, katta fayl) butun xotiraga sig'maydi (10 GB fayl — 8 GB xotira); yoki dastur asta xotira yeydi (leak — soatlar davomida yiqiladi). Xotira — tezlik kabi optimallashtiriladigan resurs (nafaqat CPU). Xotira-samarali kod — katta ma'lumot bilan ishlaydi (kichik xotirada), barqaror (yiqilmaydi). Xotira — cheklangan, muhim resurs. Kam xotira — barqaror.
2.2. Generatorlar (oqim)
Butun ma'lumotni yuklamaslik:
# YOMON: butun faylni xotiraga (katta — halokat)
qatorlar = list(open("katta.csv")) # 10 GB xotirada
# YAXSHI: generator — qator-qator (oqim)
for qator in open("katta.csv"): # bir vaqtda bir qator
qayta_ishla(qator) # kichik xotira Generatorlar (13-qism) — ma'lumotni oqim (stream) sifatida, butun yuklamasdan qayta ishlash: list(...) (butun ma'lumot xotirada — katta) o'rniga generator (for x in ..., yield — bir vaqtda bir element). Sabab: katta ma'lumot (million qator, katta fayl) butun yuklash — halokat (xotira tugaydi); generator har elementni kerak bo'lganda beradi (oqim — bir vaqtda bitta, xotira kichik). Masalan 10 GB fayl generator bilan 10 MB xotirada (bir qator). Bu xotira optimizatsiyasining eng kuchli usuli (katta ma'lumot uchun). Generator — oqim (butun emas). Bir vaqtda bir element — kichik xotira.
2.3. Xotira o'lchash
Nima qancha xotira:
import sys
sys.getsizeof([1, 2, 3]) # obyekt hajmi (bayt)
sys.getsizeof("salom")
# tracemalloc 29.2-bob — qayerda ko'p xotira
import tracemalloc
tracemalloc.start()
# ... kod ...
joriy, eng_yuqori = tracemalloc.get_traced_memory() Xotira o'lchash — optimizatsiyani o'lchashdan boshlash (29.1 kabi — nima og'ir?): sys.getsizeof(obyekt) (obyekt xotirasi — bayt), tracemalloc (29.2 — dastur xotira sarfi, eng ko'p olgan joylar), memory_profiler (qator bo'yicha). Sabab: xotira muammosini tuzatish uchun qayerda ko'p (taxmin emas — 29.1); o'lchamasdan optimizatsiya — ko'r. Odatiy og'ir joylar: katta ro'yxatlar, ko'p obyekt, keraksiz nusxalar, kesh 29.3-bob. Avval o'lcha, keyin optimallashtir 29.1-bob. Xotira o'lchash — muammo manzilini topish. O'lchash — optimizatsiya asosi.
2.4. __slots__ (ixcham obyekt)
Obyekt xotirasini kamaytirish:
# ODATIY obyekt — __dict__ (moslashuvchan, lekin katta)
class Nuqta:
def __init__(self, x, y): self.x = x; self.y = y
# __slots__ — belgilangan maydonlar (ixcham, kam xotira)
class Nuqta:
__slots__ = ("x", "y") # __dict__ yo'q — kam xotira
def __init__(self, x, y): self.x = x; self.y = y __slots__ — obyekt xotirasini kamaytirish: odatiy Python obyekti har birida __dict__ (lug'at — moslashuvchan, istalgan atribut, lekin katta — har obyekt lug'at); __slots__ maydonlarni oldindan belgilaydi (__slots__ = ("x", "y")) — __dict__ yaratilmaydi (ixcham, kam xotira). Sabab: ko'p obyekt (million nuqta, foydalanuvchi) — har birida __dict__ katta (jami ko'p xotira); __slots__ buni keskin kamaytiradi (2-3 barobar). Ehtiyot: __slots__ moslashuvchanlikni kamaytiradi (yangi atribut qo'shib bo'lmaydi) — faqat ko'p, sodda obyektga. __slots__ — ixcham obyekt (ko'p obyektga). Belgilangan maydon — kam xotira.
2.5. Ma'lumot tuzilmalari
To'g'ri tuzilma tanlash:
| Tuzilma | Xotira/tezlik |
|---|---|
| list | Moslashuvchan, o'rta xotira |
| set/dict | Tez qidiruv (O(1)), ko'proq xotira |
| tuple | O'zgarmas, kam xotira (list'dan) |
| array | Raqamlar — ixcham (list'dan kam) |
| generator | Oqim — eng kam (yuklamaydi) |
Ma'lumot tuzilmalari — to'g'ri tuzilma xotira va tezlikni belgilaydi: list (moslashuvchan, o'rta xotira), set/dict (tez qidiruv O(1), lekin ko'proq xotira — hash), tuple (o'zgarmas — list'dan kam xotira), array (bir xil turdagi raqamlar — list'dan ancha kam, ixcham), generator (oqim — eng kam, yuklamaydi — 29.9.2), bytes (matn/ikkilik — ixcham). Sabab: har tuzilma xotira/tezlik savdosi (29.3 — time-space) — to'g'ri tanlov muhim (million raqam list vs array — katta farq). Ish turiga qarab (qidiruv — set, raqamlar — array, oqim — generator). Tuzilma — xotira va tezlik. To'g'ri tuzilma — samarali.
2.6. Xotira oqishi (memory leak)
Keraksiz havolalar:
# xotira oqishi — obyektlar o'chmaydi (havola qoladi)
kesh = {}
def qayta_ishla(data):
kesh[data.id] = data # kesh o'smoqda (hech o'chmaydi!)
# → xotira asta to'ladi (leak)
# yechim: cheklangan kesh (LRU — 29.3), havolani tozalash Xotira oqishi (memory leak) — obyektlar o'chmasligi (havola qoladi — Python garbage collector o'chirolmaydi): masalan cheksiz o'suvchi kesh (kesh[id] = data — hech o'chmaydi), global ro'yxatga qo'shib borish, aylanma havolalar (circular reference). Natija: xotira asta to'ladi (soatlar/kunlar davomida — uzoq ishlayotgan server), oxirda yiqiladi (OOM). Sabab: Python obyektni havola bo'lsa o'chirmaydi (garbage collection — havola yo'q bo'lganda); keraksiz havola — leak. Yechim: cheklangan kesh (LRU — 29.3), havolani tozalash (del, weakref), profiling (29.2 — xotira o'sishi). Memory leak — asta xotira to'lishi. Keraksiz havola — leak.
2.7. Xotira optimizatsiyasi amaliyoti
Xotira optimizatsiyasi amaliyotlari: o'lcha avval (29.1 — sys.getsizeof, tracemalloc — qayerda ko'p); generator (katta ma'lumot — oqim, butun yuklamas); __slots__ (ko'p obyekt — ixcham); to'g'ri tuzilma (raqamlar — array, qidiruv — set); kesh cheklovi (LRU — 29.3, cheksiz emas); havolani tozalash (leak oldini — del, weakref); lazy loading (kerak bo'lganda yuklash); xotira monitoring (28.10 — prodda xotira, leak). Tuzoqlar: butun yuklash (katta ma'lumot — generator), cheksiz kesh (leak), __slots__siz ko'p obyekt. Yaxshi xotira optimizatsiyasi — o'lchash, generator, ixcham. Amaliyot — xotira-samarali kod. O'lcha, oqim, ixcham.
2.8. Xotira — vaqt bilan muvozanat
Xotira optimizatsiyasi asosiy g'oyasi — xotira va vaqt muvozanati (time-space tradeoff — 29.3): ba'zan vaqtni tejash uchun xotira ishlatiladi (kesh — 29.3, oldindan hisoblash), ba'zan xotirani tejash uchun vaqt (generator — qayta o'qish, siqish). To'g'ri muvozanat kontekstga bog'liq (xotira cheklangan bo'lsa — generator; tezlik muhim bo'lsa — kesh). Bu unumdorlik (29.1 — o'lchash), profiling (29.2 — xotira), kesh (29.3 — xotira narxi) bilan bir tizim. "Xotira ham tezlik kabi resurs" (optimallashtiriladigan). Katta ma'lumot davrida (big data, ML) xotira optimizatsiyasi kritik. Xotira optimizatsiyasi — resursni muvozanatlash. Vaqt vs xotira — kontekstga qarab.
3. Tez ma'lumotnoma
import sys
# XOTIRA O'LCHASH:
sys.getsizeof(obyekt) # obyekt hajmi (bayt)
import tracemalloc; tracemalloc.start() # dastur xotirasi
# GENERATOR (oqim — butun yuklamaydi):
def oqi(fayl):
for qator in open(fayl): # bir vaqtda bir qator
yield qayta_ishla(qator)
# list(...) — butun xotirada (katta) · generator — oqim (kichik)
# __SLOTS__ (ixcham obyekt — ko'p obyektga):
class Nuqta:
__slots__ = ("x", "y") # __dict__ yo'q (kam xotira)
# TUZILMALAR (xotira/tezlik):
# list (moslashuvchan) · tuple (kam) · array (raqamlar ixcham)
# set/dict (tez qidiruv, ko'p xotira) · generator (oqim, eng kam)
# MEMORY LEAK: cheksiz kesh, global ro'yxat → asta to'ladi
# yechim: LRU kesh, del, weakref
# PRINSIP: o'lcha → generator (katta) → __slots__ (ko'p obyekt)Xotira optimizatsiyasi xulosasi
Xotira — cheklangan resurs (tugasa yiqiladi — OOM)
Generator (oqim — butun yuklamaydi, katta ma'lumot uchun)
__slots__ (ixcham obyekt — ko'p obyektga) · to'g'ri tuzilma
Memory leak (cheksiz kesh, havola — asta to'ladi)
O'lcha (getsizeof, tracemalloc) · vaqt-xotira muvozanati4. Batafsil misollar
Misollar sof Python (
sys.getsizeof, generatorlar) bilan xotira mantiqini ko'rsatadi.
Misol 1 — Generator vs ro'yxat (xotira)
"""Generator: oqim (bir element) vs ro'yxat (butun) — xotira farqi."""
import sys
def royxat_usul(n: int) -> list:
# butun ro'yxat xotirada
return [x * x for x in range(n)]
def generator_usul(n: int):
# generator — bir vaqtda bir element (yield)
return (x * x for x in range(n))
def main() -> None:
n = 1000
print("=== 1. Ro'yxat (butun xotirada) ===")
royxat = royxat_usul(n)
print(f" hajm: {sys.getsizeof(royxat)} bayt ({n} element)")
print("\n=== 2. Generator (oqim) ===")
gen = generator_usul(n)
print(f" hajm: {sys.getsizeof(gen)} bayt (bir vaqtda bir element)")
print("\n=== 3. Farq ===")
royxat_hajm = sys.getsizeof(royxat)
gen_hajm = sys.getsizeof(gen)
print(f" ro'yxat: {royxat_hajm}, generator: {gen_hajm}")
print(f" generator ~{royxat_hajm // gen_hajm}x kichik")
print("\n=== 4. Katta ma'lumot ===")
print(" million element: ro'yxat — MB, generator — baytlar")
print(" generator butun yuklamaydi (oqim)")
print(" ⭐ Generator — oqim (kichik xotira)")
if __name__ == "__main__":
main()Natijaning muhim qismi:
=== 1. Ro'yxat (butun xotirada) ===
hajm: 8856 bayt (1000 element)
=== 2. Generator (oqim) ===
hajm: 208 bayt (bir vaqtda bir element)
=== 3. Farq ===
ro'yxat: 8856, generator: 208
generator ~42x kichik
=== 4. Katta ma'lumot ===
million element: ro'yxat — MB, generator — baytlar
generator butun yuklamaydi (oqim)
⭐ Generator — oqim (kichik xotira)Nima ko'rsatdi: 2.2, 2.3-bo'limlar.
Misol 2 — slots (ixcham obyekt)
"""__slots__: obyekt xotirasini kamaytirish (__dict__ o'rniga)."""
import sys
class OddiyNuqta:
# __dict__ bilan (moslashuvchan, katta)
def __init__(self, x: int, y: int) -> None:
self.x = x
self.y = y
class SlotsNuqta:
# __slots__ (ixcham, __dict__ yo'q)
__slots__ = ("x", "y")
def __init__(self, x: int, y: int) -> None:
self.x = x
self.y = y
def main() -> None:
oddiy = OddiyNuqta(1, 2)
slots = SlotsNuqta(1, 2)
print("=== 1. Oddiy obyekt (__dict__) ===")
print(f" __dict__ bor: {hasattr(oddiy, '__dict__')}")
print(f" __dict__ hajmi: {sys.getsizeof(oddiy.__dict__)} bayt")
print("\n=== 2. __slots__ obyekt ===")
print(f" __dict__ bor: {hasattr(slots, '__dict__')}")
print(" __dict__ yo'q (ixcham)")
print("\n=== 3. Ko'p obyekt ta'siri ===")
print(" million nuqta: oddiy — har birida __dict__ (katta)")
print(" __slots__ — belgilangan maydon (2-3x kam)")
print("\n=== 4. Ehtiyot ===")
print(" __slots__ — yangi atribut qo'shib bo'lmaydi")
print(" faqat ko'p, sodda obyektga")
print(" ⭐ __slots__ — ixcham obyekt (ko'p obyektga)")
if __name__ == "__main__":
main()Natijaning muhim qismi:
=== 1. Oddiy obyekt (__dict__) ===
__dict__ bor: True
__dict__ hajmi: 296 bayt
=== 2. __slots__ obyekt ===
__dict__ bor: False
__dict__ yo'q (ixcham)
=== 3. Ko'p obyekt ta'siri ===
million nuqta: oddiy — har birida __dict__ (katta)
__slots__ — belgilangan maydon (2-3x kam)
=== 4. Ehtiyot ===
__slots__ — yangi atribut qo'shib bo'lmaydi
faqat ko'p, sodda obyektga
⭐ __slots__ — ixcham obyekt (ko'p obyektga)Nima ko'rsatdi: 2.4-bo'lim.
Misol 3 — Ma'lumot tuzilmalari (xotira)
"""Tuzilmalar: turli tuzilma xotirasi (to'g'ri tanlov muhim)."""
import sys
from array import array
def main() -> None:
raqamlar = list(range(100))
print("=== 1. list (moslashuvchan) ===")
list_hajm = sys.getsizeof(raqamlar)
print(f" hajm: {list_hajm} bayt")
print("\n=== 2. tuple (o'zgarmas — kam) ===")
tuple_hajm = sys.getsizeof(tuple(raqamlar))
print(f" hajm: {tuple_hajm} bayt")
print("\n=== 3. array (raqamlar — ixcham) ===")
arr = array("i", raqamlar) # butun sonlar
array_hajm = sys.getsizeof(arr)
print(f" hajm: {array_hajm} bayt")
print("\n=== 4. Taqqoslash ===")
print(f" list: {list_hajm}, tuple: {tuple_hajm}, array: {array_hajm}")
print(f" tuple < list (o'zgarmas)")
print(" array — raqamlar uchun ixcham (list'dan kam)")
print(" ma'lumot turiga qarab tuzilma")
print(" ⭐ To'g'ri tuzilma — kam xotira")
if __name__ == "__main__":
main()Natijaning muhim qismi:
=== 1. list (moslashuvchan) ===
hajm: 856 bayt
=== 2. tuple (o'zgarmas — kam) ===
hajm: 848 bayt
=== 3. array (raqamlar — ixcham) ===
hajm: 480 bayt
=== 4. Taqqoslash ===
list: 856, tuple: 848, array: 480
tuple < list (o'zgarmas)
array — raqamlar uchun ixcham (list'dan kam)
ma'lumot turiga qarab tuzilma
⭐ To'g'ri tuzilma — kam xotiraNima ko'rsatdi: 2.5-bo'lim.
Misol 4 — Xotira oqishi (memory leak)
"""Memory leak: cheksiz kesh asta xotira yeydi (cheklash bilan yechim)."""
from collections import OrderedDict
class LeakliKesh:
"""Cheksiz kesh — memory leak (hech o'chmaydi)."""
def __init__(self) -> None:
self.kesh: dict = {}
def qosh(self, kalit: int, data: str) -> None:
self.kesh[kalit] = data # cheksiz o'sadi (leak!)
class CheklanganKesh:
"""Cheklangan kesh (LRU) — xotira barqaror."""
def __init__(self, sigim: int) -> None:
self.sigim = sigim
self.kesh: OrderedDict = OrderedDict()
def qosh(self, kalit: int, data: str) -> None:
self.kesh[kalit] = data
if len(self.kesh) > self.sigim:
self.kesh.popitem(last=False) # eng eski o'chadi
def main() -> None:
print("=== 1. Leakli kesh (cheksiz o'sadi) ===")
leak = LeakliKesh()
for i in range(1000):
leak.qosh(i, f"data-{i}")
print(f" 1000 qo'shildi → kesh hajmi: {len(leak.kesh)} (hammasi!)")
print("\n=== 2. Cheklangan kesh (LRU) ===")
cheklangan = CheklanganKesh(sigim=100)
for i in range(1000):
cheklangan.qosh(i, f"data-{i}")
print(f" 1000 qo'shildi → kesh hajmi: {len(cheklangan.kesh)} (chegarada)")
print("\n=== 3. Farq ===")
print(f" leakli: {len(leak.kesh)} (asta to'ladi — OOM)")
print(f" cheklangan: {len(cheklangan.kesh)} (barqaror)")
print("\n=== 4. Memory leak sababi ===")
print(" havola qoladi → o'chmaydi (garbage collector)")
print(" yechim: cheklangan kesh (LRU), del, weakref")
print(" ⭐ Memory leak — cheksiz o'sish (cheklash yechim)")
if __name__ == "__main__":
main()Natijaning muhim qismi:
=== 1. Leakli kesh (cheksiz o'sadi) ===
1000 qo'shildi → kesh hajmi: 1000 (hammasi!)
=== 2. Cheklangan kesh (LRU) ===
1000 qo'shildi → kesh hajmi: 100 (chegarada)
=== 3. Farq ===
leakli: 1000 (asta to'ladi — OOM)
cheklangan: 100 (barqaror)
=== 4. Memory leak sababi ===
havola qoladi → o'chmaydi (garbage collector)
yechim: cheklangan kesh (LRU), del, weakref
⭐ Memory leak — cheksiz o'sish (cheklash yechim)Nima ko'rsatdi: 2.6-bo'lim.
5. To'g'ri va noto'g'ri tushunishlar
| Noto'g'ri fikr | To'g'risi |
|---|---|
| "Faqat tezlik muhim" | Xotira ham (cheklangan) |
| "Butun ma'lumotni yukla" | Generator (oqim — katta uchun) |
| "Obyekt xotirasi bir xil" | __slots__ (ixcham) |
| "Har tuzilma bir xil" | To'g'ri tanlov (array, set) |
| "Kesh cheksiz" | Cheklangan (LRU — leak) |
| "Python leak yo'q" | Havola — leak |
| "Xotira o'lchamasdan" | O'lcha (getsizeof, tracemalloc) |
"__slots__ har obyektga" |
Ko'p, sodda obyektga |
6. Keng tarqalgan xatolar va yechimlari
1. Butun ma'lumotni yuklash
qatorlar = list(open("katta.csv")) # OOM # ⚠️
for qator in open("katta.csv"): ... # generator # ✅2. Cheksiz kesh (leak)
kesh[id] = data # hech o'chmaydi (asta to'ladi) # ⚠️
# LRU kesh (cheklangan — 29.3) # ✅3. Ko'p obyekt __slots__siz
# million obyekt, har birida __dict__ (katta) # ⚠️
class X: __slots__ = (...) # ixcham # ✅4. Noto'g'ri tuzilma (raqamlar)
raqamlar = [1, 2, ...] # list (katta — million raqam) # ⚠️
array("i", raqamlar) # ixcham # ✅5. Xotira o'lchamasdan optimizatsiya
# "bu ko'p xotira yeydi" (taxmin) # ⚠️
tracemalloc / getsizeof # o'lcha 29.1-bob # ✅6. Keraksiz nusxalar
yangi = data[:] # har safar nusxa (xotira) # ⚠️
# o'rniga havola yoki generator (nusxasiz) # ✅7. Global o'suvchi ro'yxat
JURNAL = [] # har so'rov qo'shadi (cheksiz — leak) # ⚠️
# cheklangan (deque maxlen) yoki tashqi log # ✅7. Integratsiya — bu bilim qayerda kerak bo'ladi
- 13-qism (o'tilgan): Generatorlar, iteratorlar
- 29.2-dars (o'tilgan): Profiling — xotira profiling
- 29.3-dars (o'tilgan): Kesh — xotira narxi (time-space)
- 24-qism (o'tilgan): Ma'lumot tahlili — katta ma'lumot
- 28.10-dars (o'tilgan): Monitoring — xotira, leak
8. Eng yaxshi amaliyotlar
O'lcha avval (getsizeof, tracemalloc).
Generator (katta ma'lumot — oqim).
__slots__(ko'p obyekt — ixcham).To'g'ri tuzilma (array, set — ish turiga).
Kesh cheklovi (LRU — leak oldini).
Havolani tozalash (del, weakref).
Lazy loading (kerak bo'lganda).
Xotira monitoring (prodda — leak).
9. Amaliy topshiriq
Vazifa 1: Bashorat qiling
1. # nega xotira muhim?
2. # OOM nima?
3. # generator nima (xotira)?
4. # list vs generator?
5. # getsizeof nima?
6. # __slots__ nima?
7. # __slots__ nega kam xotira?
8. # array vs list?
9. # memory leak nima?
10. # leak sababi?
11. # leak yechimi?
12. # time-space tradeoff?Javoblar
- Cheklangan resurs (tugasa yiqiladi)
- Out of memory (xotira tugadi)
- Oqim — bir vaqtda bir element (butun emas)
- list butun xotirada, generator oqim
- Obyekt xotirasi (bayt)
- Obyekt maydonlarini belgilash (ixcham)
- dict yaratmaydi (har obyekt lug'at)
- array raqamlar uchun ixcham (list'dan kam)
- Obyektlar o'chmaydi (havola qoladi)
- Cheksiz kesh, global ro'yxat, havola
- Cheklangan kesh (LRU), del, weakref
- Vaqt vs xotira muvozanati
Vazifa 2: Xatolarni tuzating
1. qatorlar = list(open("katta.csv"))
2. kesh[id] = data # cheksiz
3. # million obyekt __slots__siz
4. raqamlar = [1, 2, ...] # million
5. # "ko'p xotira" (taxmin)Javoblar
1. for qator in open(...) # generator
2. LRU kesh (cheklangan)
3. __slots__ (ixcham)
4. array("i", raqamlar)
5. tracemalloc yoki getsizeof bilanVazifa 3: Generator
Modellang:
- Ro'yxat
- Generator
- Xotira
- Farq
Vazifa 4: slots
Modellang:
- Oddiy
- slots
- dict
- Xotira
Vazifa 5: Tuzilmalar
Modellang:
- list
- tuple
- array
- Taqqoslash
Vazifa 6: Memory leak
Modellang:
- Leakli kesh
- Cheklangan
- O'sish
- Yechim
Vazifa 7: O'ylash
Xotira optimizatsiyasida generatorlar (oqim) kuchli vosita — 10 GB faylni 10 MB xotirada qayta ishlash mumkin. Nima uchun "butun ma'lumotni yuklash o'rniga oqim (bir vaqtda bir element)" katta ma'lumot davrida (big data) shunchalik muhim tamoyil, va nega "xotira va vaqt muvozanati" (time-space tradeoff) optimizatsiyaning tub xususiyati — biror narsani tejash uchun boshqasini sarflash nega muqarrar?
Javob
Qisqa javob: "Oqim (bir vaqtda bir element)" katta ma'lumot davrida muhim, chunki: ma'lumot hajmi xotiradan katta bo'lishi mumkin (10 GB fayl, 8 GB xotira; yoki cheksiz oqim — real vaqt hodisalari) — butun yuklash imkonsiz (sig'maydi). Oqim (generator) ma'lumotni qism-qism qayta ishlaydi (bir vaqtda bir element) — xotira hajmga bog'liq emas (doimiy, kichik — bir element); 10 GB ham, 10 TB ham bir xil kichik xotira (har element o'tadi, ketadi). Bu miqyoslanuvchanlik: butun yuklash — xotira ma'lumot hajmiga proporsional (O(n) xotira — miqyoslanmaydi); oqim — doimiy xotira (O(1) — miqyoslanadi, cheksiz ma'lumot). Big data (katta ma'lumot) da ma'lumot doim xotiradan katta — oqim majburiy. "Xotira va vaqt muvozanati" (time-space tradeoff) optimizatsiyaning tub xususiyati, chunki: ular almashtiriladigan resurslar — biror hisoblash natijasini saqlash (xotira) qayta hisoblashni (vaqt) tejaydi (kesh — 29.3); yoki saqlamaslik (xotira tejash) qayta hisoblashni (vaqt) talab qiladi (generator — qayta o'qish). Ikkalasini birga tejab bo'lmaydi (odatda) — chunki natijani ishlatish uchun u biror joyda bo'lishi kerak (xotirada — tez, lekin joy; yoki qayta hisoblanadi — joy yo'q, lekin vaqt). Bu fizik cheklov (ma'lumot yo saqlanadi — joy, yo hisoblanadi — vaqt; uchinchi yo'l yo'q). Shuning uchun optimizatsiya — savdo (bir resursni boshqasiga almashtirish, kontekstga qarab): xotira cheklangan bo'lsa — vaqt sarfla (generator, siqish); vaqt muhim bo'lsa — xotira sarfla (kesh, oldindan hisoblash). "Bepul tushlik yo'q" (no free lunch) — har yaxshilanish narx bilan. Muhandislik saboqlari: oqim — doimiy xotira (miqyoslanadi, katta ma'lumot); butun yuklash — proporsional xotira (miqyoslanmaydi); time-space — almashtiriladigan resurslar (biror narsani tejash — boshqasini sarflash); optimizatsiya — savdo (kontekstga qarab tanlash), bepul yaxshilanish yo'q.
1. Nega oqim muhim (big data)
Ma'lumot hajmi xotiradan katta (10 GB fayl, cheksiz oqim). Butun yuklash imkonsiz. Oqim — qism-qism (xotira hajmga bog'liq emas).
2. Miqyoslanuvchanlik
| Usul | Xotira |
|---|---|
| Butun yuklash | O(n) — hajmga proporsional (miqyoslanmaydi) |
| Oqim (generator) | O(1) — doimiy (miqyoslanadi) |
3. Nega time-space tradeoff tub
Xotira va vaqt — almashtiriladigan. Saqlash (xotira) → vaqt tejaydi (kesh). Saqlamaslik (xotira tejash) → vaqt sarflaydi (qayta hisoblash).
4. Nega muqarrar
Natija biror joyda bo'lishi kerak: xotirada (tez, joy) yoki hisoblanadi (joy yo'q, vaqt). Uchinchi yo'l yo'q (fizik cheklov).
5. Muhandislik saboqlari
- Oqim — doimiy xotira (miqyoslanadi)
- Butun yuklash — proporsional (miqyoslanmaydi)
- Time-space — almashtiriladigan resurslar
- Optimizatsiya — savdo (bepul tushlik yo'q)
6. Xulosa
- Oqim — hajmdan mustaqil xotira (big data)
- Butun yuklash — imkonsiz (katta ma'lumot)
- Time-space — resurslar almashtiriladigan (muqarrar savdo)
- Kontekstga qarab tanlash (xotira yoki vaqt)
Nimani mustahkamlaydi: 2.2, 2.8-bo'limlar.
Xulosa
Bu darsda xotira optimizatsiyasini o'rgandik.
Eng muhim uch fikr:
Nega xotira va generatorlar. Xotira cheklangan resurs (tugasa dastur yiqiladi — OOM, yoki svop — sekin); katta ma'lumot butun yuklash — halokat (10 GB fayl, 8 GB xotira), yoki asta xotira yeydi (leak). Xotira — tezlik kabi optimallashtiriladigan resurs. Generatorlar (13-qism) — ma'lumotni oqim sifatida, butun yuklamasdan (
list(...)o'rnigayield— bir vaqtda bir element); katta ma'lumot (million qator, 10 GB fayl) generator bilan kichik xotirada (bir element); eng kuchli usul (katta ma'lumot uchun).O'lchash, slots, tuzilmalar. Xotira o'lchash —
sys.getsizeof(obyekt)(obyekt hajmi),tracemalloc(29.2 — dastur xotirasi, eng ko'p joylar); avval o'lcha 29.1-bob.__slots__— obyekt xotirasini kamaytirish (odatiy obyekt__dict__— katta;__slots__ = ("x", "y")—__dict__yo'q, ixcham, 2-3x kam); faqat ko'p, sodda obyektga (moslashuvchanlikni kamaytiradi). Ma'lumot tuzilmalari: list (moslashuvchan), tuple (o'zgarmas — kam), array (raqamlar — ixcham), set/dict (tez qidiruv, ko'p xotira), generator (oqim — eng kam); ish turiga qarab tanlash.Memory leak va muvozanat. Xotira oqishi (memory leak) — obyektlar o'chmasligi (havola qoladi — cheksiz kesh, global ro'yxat, aylanma havola); xotira asta to'ladi (uzoq ishlayotgan server — OOM); yechim: cheklangan kesh (LRU — 29.3), havolani tozalash (
del,weakref), profiling 29.2-bob. Xotira optimizatsiyasi — xotira va vaqt muvozanati (time-space tradeoff — 29.3): vaqt tejash uchun xotira (kesh) yoki xotira tejash uchun vaqt (generator — qayta o'qish); almashtiriladigan resurslar (biror narsani tejash — boshqasini sarflash, bepul tushlik yo'q). Oqim — doimiy xotira (miqyoslanadi, katta ma'lumot — O(1)); butun yuklash — proporsional (O(n) — miqyoslanmaydi). "Xotira ham tezlik kabi resurs" (big data, ML davrida kritik).
Keyingi darsda benchmark va yuk testini o'rganamiz: tizim unumdorligini sinash — benchmark (nazorat sinovi), yuk testi (load testing — ko'p foydalanuvchi simulyatsiyasi), stress testi va tizim chegaralarini topish.
Izohlar (0)
Izoh yozish uchun kiring.
- Hozircha izoh yo'q. Birinchi bo'ling!