Barcha qo'llanmalar

Python'dagi KeyError exception'lari: sabablari va ularni tuzatish usullari

Python'dagi KeyError bilan qiynalyapsizmi? Tushib qolgan key'lardan tortib type nomuvofiqligigacha — u nima sababdan yuzaga kelishini bilib oling va kodingizda uni tuzatishning 3 ta oddiy usulini o'zlashtiring.

Muallif: Kimberly Fessel

Tan olaylik — Python xatolari rosa jonga tegishi mumkin. Kod mantiqingizni mukammal qilish va sintaksisni to'g'ri yozishga vaqt sarflaysiz-u, dasturingizni yo'lda to'xtatib qo'yadigan bug'ga duch kelasiz. Keng tarqalgan exception'lardan biri — KeyError; u dictionary'dagi mavjud bo'lmagan key'ga murojaat qilmoqchi bo'lganingizda yuzaga keladi. Bu asabni buzadi, ammo xatolar har doim ham yomon narsa emas. Agar Python exception'lari nimani anglatishi, nega yuzaga kelishi va ularni qanday tuzatish mumkinligini tushunishga vaqt ajratsangiz, ular qimmatli debugging vositasiga aylanadi.

Ushbu maqolada Python'dagi KeyError exception'ini chuqur o'rganamiz. Sizga KeyError traceback'ini qanday o'qishni ko'rsatamiz va KeyError raise qiladigan eng keng tarqalgan vaziyatlarni tushuntiramiz. Shuningdek, KeyError exception handling uchun qadamma-qadam yechimlarni ko'rib chiqamiz. Keling, avvalo KeyError aynan nima ekanini va Python ularni nega raise qilishini tushunib olishdan boshlaylik.

KeyError exception'i nima?

Python'da KeyError mapping obyektida, masalan, dictionary'da — Python'ning built-in hashmap'ida mavjud bo'lmagan key'ga murojaat qilmoqchi bo'lganingizda yuzaga keladi. Bu siz murojaat qilgan key mapping'da mavjud emasligini bildiruvchi exception. Bu quyidagicha sodir bo'lishi mumkin:

drink_prices = {"coffee": 3.50}

print(drink_prices["tea"])

# Expected result:
# KeyError: 'tea'

drink_prices dictionary'sida 'tea' key'i ham, unga bog'langan value ham yo'q, shuning uchun Python KeyError raise qiladi.

KeyError traceback'ini qanday o'qish kerak

Python KeyError raise qilganda u xato qayerda yuz berganini va muammoga qaysi key sabab bo'lganini topishga yordam beradigan traceback ham hosil qiladi. Masalan, drink_prices misolimiz uchun to'liq traceback quyidagicha:

drink_prices = {"coffee": 3.50}

print(drink_prices["tea"])

# Expected result (full traceback):
# Traceback (most recent call last):
#    File "<python-input-0>", line 3, in <module>
#      print(drink_prices["tea"])
            ~~~~~~~~~~~~^^^^^^^
# KeyError: 'tea'

Noto'g'ri Python kodini ko'rsatadigan syntax error'lardan farqli o'laroq, KeyError traceback'lari dastur ishlayotgan paytda lookup qayerda muvaffaqiyatsiz bo'lganini topishga yordam beradi. Traceback'ni o'qish uchun qadamma-qadam yondashuv:

  1. Oxirgi qatorni o'qing. Traceback'ning oxirgi qatorida exception type'i va qo'shimcha tafsilotlar bo'ladi. Bu yerda bizda KeyError bor, 'tea' esa tushib qolgan key.

  2. Xatoga sabab bo'lgan qatorni toping. Traceback 3-qatorni ko'rsatadi — aynan shu yerda Python 'tea' key'iga murojaat qilmoqchi bo'lgan.

  3. Tushib qolgan key'ni qayd eting. Python 'tea''ni topa olmayapti, shuning uchun biz uni dictionary'mizga qo'shishimiz yoki uni so'ramasligimiz kerak.

Xatoni keltirib chiqargan qatorni va qaysi key tushib qolganini qayd etganingizdan so'ng, keyingi qadam — key nega mavjud emasligini aniqlash. Keling, KeyError'ning eng keng tarqalgan sabablarini ko'rib chiqaylik. SyntaxError traceback'ini o'qish boshqacha ishlaydi, chunki bu xato kod ishga tushishidan oldin raise qilinadi.

Python'da KeyError exception'lari nega yuzaga keladi: sabablar

KeyErrors dictionary yoki Counter kabi mapping obyektida mavjud bo'lmagan key'ga murojaat qilmoqchi bo'lganingizda yuzaga keladi. Mapping bo'lmagan ba'zi obyektlar, jumladan pandas DataFrame'lari ham lookup muvaffaqiyatsiz bo'lganda KeyError exception'ini raise qilishi mumkin. Ushbu bo'lim davomida asosan dictionary'larga e'tibor qaratamiz, ammo boshqa obyektlarda ham asosiy sabab shunga o'xshash. Aksariyat hollarda muammo tushib qolgan key'lar, type nomuvofiqligi, kutilmagan whitespace yoki katta-kichik harflardagi farqlarga borib taqaladi.

Dictionary'da key mavjud emas

Python KeyError raise qilishining eng keng tarqalgan stsenariysi — dictionary ichida mavjud bo'lmagan key'ga murojaat qilganingizda. Aytaylik, sizda foydalanuvchilarning login ma'lumotlari saqlangan ma'lumotlar bazasi bor. Agar yangi foydalanuvchi ro'yxatdan o'tmasdan tizimga kirmoqchi bo'lsa, KeyError so'ralgan key dictionary'da yo'qligini bildiradi:

user_credentials = {
    "user001": "pAs$wurD",
    "user002": "password12345",
    "user003": "my_pass"
}

def login(username, password):
    if user_credentials[username] == password:
        return "Login successful"
    return "Login failed"

print(login("user004", "test"))

# Expected result:
# KeyError: 'user004'

user_credentials dictionary'sida "user004" key'i yo'q va u bu key'ning value'sini qaytara olmaydi. Shuning uchun Python unga murojaat qilmoqchi bo'lganda KeyError raise qiladi.

Type nomuvofiqligi

Python'dagi ko'plab KeyError muammolari oddiygina tushib qolgan key'lardan kelib chiqsa-da, boshqalari nozikroq va shu sababli ularni debug qilish qiyinroq. Quyidagi kodni ko'rib chiqing:

color_mapper = {
    "0": "black",
    "1": "blue",
    "2": "orange"
}

print(color_mapper[0])

# Expected result:
# KeyError: 0

Bu kod nolga bog'langan rangni topishga harakat qiladi, ammo muvaffaqiyatsiz bo'ladi, chunki color_mapper'dagi key'lar integer'lar (0) emas, balki string'lar ("0", "1", "2"). Python key'ning, jumladan data type'ining ham aniq mos kelishini talab qiladi; aks holda u KeyError exception'ini raise qiladi.

Bunday muammo ko'pincha pandas DataFrame'lari bilan ishlaganda uchraydi: u yerda ustun label'lari string bo'lishi mumkin, kodingiz esa integer'lardan foydalanadi (yoki aksincha). Ma'lumotlarga murojaat qilishdan oldin key'lar yoki ustun nomlarining type'i va formatini tekshirib olish muhim.

Whitespace yoki katta-kichik harflarga sezgirlik

Type nomuvofiqliklari bilan bir qatorda, whitespace va harflarning katta-kichikligi kabi nozik formatlash farqlari ham Python'da KeyError exception'lariga olib kelishi mumkin. Mana tushunarli misol:

student_scores = {
    " TOM ": 79,
    " TONY ": 92,
    " TERESA ": 84 
}

print(student_scores["Tom"])

# Expected result:
# KeyError: 'Tom'

Dictionary key'larida ortiqcha whitespace va katta harflar bor (masalan, " TOM "), kod esa "Tom"'ga murojaat qilmoqchi bo'ladi. Key value'larini qidirishda whitespace ham, harflarning katta-kichikligi ham muhim; KeyError'dan qochish uchun ikkalasi ham to'g'ri ekaniga ishonch hosil qiling.

AI Tutor: Type, whitespace yoki katta-kichik harflardagi nomuvofiqliklar sababli yuzaga keladigan KeyError'larning beshta real misolini ko'rsating.

Tashqi manbalardan kelgan ma'lumotlar

KeyError'lar ko'pincha API'lar, JSON javoblari yoki ba'zi CSV fayllar kabi tashqi manbalardan kelgan ma'lumotlar bilan ishlaganda yuzaga keladi. Environment variable'lar ham shular qatoriga kiradi: agar o'zgaruvchi hech qachon o'rnatilmagan bo'lsa, os.environ["API_KEY"] KeyError raise qiladi. Bu ma'lumotlar tuzilmalari har doim ham bir xil bo'lavermaydi, ya'ni key'lar bitta javobda mavjud bo'lib, boshqasida bo'lmasligi mumkin. Masalan:

api_response = {
    "user": {
        "id": 1,
        "name": "Sheena" 
    }
}

print(api_response["user"]["email"])

# Expected result:
# KeyError: 'email'

"email" maydoni tashqi ma'lumot manbasiga kiritilmagan, shuning uchun key'ning value'sini olishga urinish KeyError'ga olib keladi.

KeyError exception handling strategiyalari: tuzatish usullari

Siz Python'da KeyError'ga sabab bo'lishi mumkin bo'lgan bir nechta vaziyatni ko'rdingiz. Endi KeyError exception'larini handle qilish va ularning umuman yuzaga kelishining oldini olish uchun amaliy strategiyalarni ko'rsatamiz.

Default qiymatli .get() metodi

Dictionary key'iga to'g'ridan-to'g'ri murojaat qilish o'rniga .get() metodidan foydalanishingiz mumkin. U quyidagicha ishlaydi:

drink_prices = {"coffee": 3.50}

print(drink_prices.get("coffee"))

# Expected result:
# 3.5

Key mavjud bo'lganda .get() metodi dictionary'ga to'g'ridan-to'g'ri murojaat qilish (drink_prices["coffee"]) kabi ishlaydi. Biroq to'g'ridan-to'g'ri murojaatdan farqli o'laroq, key tushib qolgan bo'lsa, u KeyError exception'ini raise qilmaydi. Buning o'rniga u default holatda None'ni yoki siz ko'rsatgan qiymatni qaytaradi.

Masalan, key topilmasa, fallback qiymat berishingiz mumkin:

drink_prices = {"coffee": 3.50}

print(drink_prices.get("tea", 4.00))

# Expected result:
# 4.0

"tea" dictionary'da bo'lmagani uchun Python KeyError raise qilish o'rniga 4.00 default qiymatini qaytaradi.

.get()'dan quyidagi hollarda foydalaning:

  • Key'ning tushib qolishi kutilgan yoki maqbul bo'lsa

  • Xato o'rniga xavfsiz qiymat olishni istasangiz

  • To'liq bo'lmagan ma'lumotlar bilan, aytaylik, API'dan kelgan ma'lumotlar bilan ishlayotgan bo'lsangiz

KeyError muammolarni ertaroq aniqlashga yordam beradigan hollarda .get()'dan foydalanmang:

  • Key'ning tushib qolishi kodingizda bug borligini anglatsa

  • Dastur to'g'ri ishlashi uchun key albatta bo'lishi shart bo'lsa

  • Nosozliklar haqida darhol bilishni istasangiz

Key'larni tekshirish uchun in'dan foydalanish

Mantiqingiz ko'proq nazoratni talab qilganda, davom etishdan oldin key dictionary'da mavjudligini tekshirish uchun conditional statement ichida in operatoridan (yoki uning teskarisi bo'lgan not in'dan) foydalanishingiz mumkin. Bu default qiymat qaytarish o'rniga tushib qolgan key'larni o'zingizning maxsus mantiqingiz yordamida hal qilish imkonini beradi. Masalan, foydalanuvchini uning ichimligi drink_prices dictionary'sida yo'qligi haqida ogohlantirishingiz va shu bilan birga default qiymatga o'tishingiz mumkin:

drink_prices = {"coffee": 3.50}

drink = "tea"

if drink in drink_prices:
    price = drink_prices[drink]
else:
    print(f"Warning: {drink} not found in price list. Using default.")
    price = 4.00

print(price)

# Expected result:
# Warning: tea not found in price list. Using default.
# 4.0

Bu yerda key'ga murojaat qilishdan oldin uning mavjudligini tekshirib, KeyError'dan qochamiz. "tea" drink_prices'da bo'lmagani uchun Python dictionary'dan uning value'sini to'g'ridan-to'g'ri qidirish o'rniga else tarmog'ini bajaradi.

Key'larni tekshirish uchun in'dan quyidagi hollarda foydalaning:

  • Tushib qolgan key uchun oddiy default qiymatdan tashqari boshqacha xatti-harakat kerak bo'lsa

  • Tushib qolgan key'larni log qilish, ular haqida ogohlantirish yoki ularni kuzatib borishni istasangiz

  • Tushib qolgan key'lar dasturingiz uchun ahamiyatga ega bo'lsa

Key'larni tekshirish uchun in'dan quyidagi hollarda foydalanmang:

  • Key'ning tushib qolishi kodingizda bug borligini anglatsa

  • Nosozliklar haqida darhol bilishni istasangiz

  • Oddiy .get() default qiymati yetarli bo'lsa

  • U hech qanday sezilarli foydasiz ortiqcha tarmoqlanishni qo'shsa

try / except

Avvaliga KeyError yuzaga kelishining oldini oladigan .get() va in'dan farqli o'laroq, try/except bloki xatoning yuzaga kelishiga yo'l qo'yadi va keyin to'g'ridan-to'g'ri exception handling'ni bajaradi. Quyidagi misol bu drink_prices uchun qanday ishlashini ko'rsatadi:

drink_prices = {"coffee": 3.50}

try:
    price = drink_prices["tea"]
except KeyError:
    price = 4.00

print(price)

# Expected result:
# 4.0

Python "tea"'ga murojaat qilishga harakat qiladi va bu KeyError exception'ini raise qiladi. Dastur crash bo'lish o'rniga boshqaruvni darhol except KeyError blokiga o'tkazadi va u yerda biz fallback qiymat beramiz. Biz xatoning oldini olmaymiz, balki u yuzaga kelgandan keyin unga javob qaytaramiz.

Best practice sifatida except blokida bare except ishlatish o'rniga exception type'ini aniq ko'rsatish (masalan, except KeyError) tavsiya etiladi. Bu faqat siz kutgan xatoni ushlashingizni ta'minlaydi.

try/except'dan quyidagi hollarda foydalaning:

  • Key'larning tushib qolishi kutilgan bo'lsa

  • Maxsus fallback mantiq yoki xabar kerak bo'lsa

  • Key tushib qolganidan keyin ham dasturingiz ishlashda davom etishini istasangiz

  • Nosozlik holatlarini oddiy key'lardan boshqacha tarzda hal qilishingiz kerak bo'lsa

try/except'dan quyidagi hollarda foydalanmang:

  • Key'ning tushib qolishi kodingizda bug borligini anglatsa

  • Nosozliklar haqida darhol bilishni istasangiz

  • Undan faqat xatolarni jimgina bostirish uchun foydalanayotgan bo'lsangiz

  • .get() yoki in tozaroq yechim bersa

Pandas'da KeyError

Agar ma'lumotlar bilan ishlash uchun pandas kutubxonasidan foydalanayotgan bo'lsangiz, KeyError odatda ustun mavjud emasligini bildiradi. Ushbu Python snippet'i kichik pandas DataFrame yaratadi va mavjud bo'lmagan "age" ustunini olishga harakat qiladi:

import pandas as pd

df = pd.DataFrame([
    {"name": "Sonny", "zip": "32814"},
    {"name": "Neela", "zip": "60602"},
])

print(df["age"])

# Expected result:
# KeyError: 'age'

pandas DataFrame dictionary bo'lmasa-da, kvadrat qavslar yordamida ustun tanlash key asosidagi lookup kabi ishlaydi, shuning uchun mavjud bo'lmagan ustunlar uchun KeyError chiqadi. Amalda pandas'dagi ko'plab KeyError muammolari ustun label'laridagi nozik nomuvofiqliklardan kelib chiqadi: masalan, harflarning noto'g'ri katta-kichikligi ("Age" va "age"), kutilmagan whitespace ("age ") yoki ustun nomlaridagi type nomuvofiqliklari.

Built-in KeyError exception'ini qachon ataylab raise qilish kerak

Boshqa built-in exception class'lari singari, foydalanuvchini noto'g'ri yoki to'liq bo'lmagan kiruvchi ma'lumot haqida ogohlantirish uchun o'z kodingizda KeyError raise qilishni tanlashingiz mumkin. Python dasturchilari buni ko'pincha kiruvchi ma'lumotlarda zarur key tushib qolganda yoki keyingi mantiq usiz xavfsiz davom eta olmaganda qiladi.

Mana konfiguratsiyaning to'rtta zarur qismini tekshiradigan va ulardan birortasi tushib qolgan bo'lsa, ataylab KeyError raise qiladigan funksiya:

def verify_config(config):
    required_keys = ["host", "port", "username", "password"]

    for key in required_keys:
        if key not in config:
            raise KeyError(f"Missing required config key: {key}")

    return config

config = {
    "host": "localhost",
    "port": 5432,
    "username": "admin"
}

verify_config(config)

# Expected result:
# KeyError: 'Missing required config key: password'

Tushib qolgan ma'lumotlar siz kutgan tuzilmani buzganda KeyError'ni ataylab raise qilish to'g'ri qadam. Bu sizga muammo haqida darhol xabar beradi va siz uni debugging uchun aniq, tushunarli xato xabari bilan moslashtirishingiz mumkin.

Xulosa

Python'ning KeyError exception'laridan asabiylashish o'rniga ularni kodingiz yashirin xatolarsiz to'g'ri ishlashini ta'minlaydigan debugging jarayonining sog'lom qismi deb hisoblang. Ular ko'pincha Python dictionary'sida tushib qolgan key'lar sababli paydo bo'ladi, ammo data type, whitespace va katta-kichik harflardagi nomuvofiqlik kabi nozikroq muammolar tufayli ham yuzaga kelishi mumkin. KeyError exception handling'da birinchi himoya chizig'ingiz sifatida traceback'ni tekshiring, ularni Python kodingizda hal qilish uchun esa .get() metodi, in keyword'i yoki try/except bloki kabi boshqa variantlarni sinab ko'ring.

Kodingizdagi KeyError muammolarini topib, ularning oldini ola olaman deb o'ylaysizmi? AI Tutor bilan muloqot qilib, ko'nikmalaringizni sinab ko'ring:

Yo'l xaritalariQo'llanmalarFAQYouTube

yo'lxaritaroadmap.shasosida

Hamjamiyat tomonidan yaratilgan yo'l xaritalari, eng yaxshi amaliyotlar, loyihalar, maqolalar, manbalar va yo'nalishlar — o'z yo'lingizni tanlash va kasbingizda o'sish uchun.

© yo'lxarita·Shartlar·Maxfiylik·

roadmap.sh

Barcha kontent roadmap.sh loyihasidan olingan (© Kamran Ahmed) va shaxsiy o'rganish uchun o'zbek tiliga tarjima qilinmoqda.

Qidiruv

Yo'l xaritalari, loyihalar va savollarni qidiring