Ачааллж байна...
String-ийн бүлгийн төгсгөлийн хичээлд бид нэг эртний өрөө барагдуулна. Бүлэг 5-д string гэдэг үгийг "утас, хэлхээ" — үсгүүд нь утсанд хэлхсэн сувд шиг дараалсан зүйл гэж тайлбарлаад, "энэ 'хэлхээ' гэдэг ойлголт гүн юм: тэмдэгт бүр байрандаа, дараалал нь чухал — Бүлэг 9-д гүнзгий ашиглана" гэж амласан. Мөн range-ийн хичээлд "эхний зүйл яагаад 0 дугаартай вэ" гэсэн асуултын биетэй хариулт "Бүлэг 9, 10-т биежинэ" гэж хойшлуулсан. Хоёулаа өнөөдөр. Сэдэв маань: индекс (index) — string-ийн тэмдэгт бүрд байдаг "байрлалын дугаар" бөгөөд түүгээр нь хэлхээнээс ганц тэмдэгтийг сугалж авч болдог юм. Өдий хүртэл бид string-тэй зөвхөн бүхлээр нь ажиллаж ирсэн: бүхлээр нь хэвлэх, бүхлээр нь томруулах, бүхлийнх нь уртыг хэмжих. Өнөөдрөөс "нарийн ажил" нээгдэнэ: эхний үсгийг нь авах, сүүлчийн үсгийг нь шалгах...
Шинэ бичиглэл нь дөрвөлжин хаалт: ner[0] — "ner-ийн 0 дугаарын тэмдэгт." Тэгээд тийм ээ: эхний тэмдэгт 0 дугаартай. Range-ийн хичээлд энэ тоолол "товчлолын учиртай" гэж хагас тайлбарлагдсан бол өнөөдөр жинхэнэ, биетэй учир нь ил гарна — тэгээд тэр ойлголт дараагийн бүлгийн list-ээс эхлээд таны бүх ирээдүйн Python-д давтагдах тул энэ хичээлд бид 0-ийн логикийг тайван, бүрэн хөгжүүлнэ.
Тоолол яагаад 0-ээс эхэлдгийг ойлгох хамгийн сайн зураг бол зам дагуух байшингийн дугаарлалт юм. Нэг гудамжинд байшингууд зэрэгцэн зогсож байна — дугаарлагч хүн хоёр өөр зарчмаар дугаарлаж болно. "Хэд дэх вэ" зарчим: эхний байшин №1, дараагийнх №2... — хүний ярианы дадал. "Эхлэлээс хэр зайтай вэ" зарчим: гудамжны эхэнд зогсоод байшин бүрээс "чи эхлэлээс хэдэн алхам зайтай вэ" гэж асууна — хамгийн эхний байшин яг эхлэл дээрээ зогсож байгаа тул хариулт нь 0 алхам: №0. Дараагийнх нь нэг алхам цаана: №1. Программчлалын ертөнц хоёр дахь зарчмыг сонгосон — индекс гэдэг нь "хэд дэх" биш "эхлэлээс хэр холдсон" гэсэн хэмжээс юм. Яагаад энэ нь дээр вэ гэдгийг нэг жишээ гайхалтай харуулдаг: range(0, len(ner)) гэхэд эхлэл 0, зогсоол len — яг string-ийн бүх индекс гарч ирдэг: хэмжээс хоорондоо "барьцалдсан" цэвэрхэн систем. "Хэд дэх" зарчмаар бол хаа сайгүй нэг нэмэх, нэг хасахын тохируулга явах байсан — off-by-one алдааны үржүүлэгч. Тиймээс 0 бол "хачин уламжлал" биш — зайн хэмжээсийн жам ёсны эхлэл юм: одометр 0-ээс эхэлдэг шиг, шугамын эхний зураас 0 байдаг шиг.
Хэлхээгээ дугаарлаж, сувд сугалъя:
python
ner = "Бат"
print(ner[0])
print(ner[1])
print(ner[2])Үр дүн:
Б
а
т"Бат" гэдэг гурван сувдтай хэлхээ: Б нь эхлэл дээрээ (индекс 0), а нь нэг алхам цаана (1), т нь хоёр алхамд (2). Бичиглэлийг задалъя: ner дөрвөлжин хаалт 0 — "ner хэлхээний 0 индексийн тэмдэгтийг өг." Дөрвөлжин хаалт бол шинэ "дуудлагын хэлбэр": дугуй хаалт function дууддаг, цэг авдар нээдэг байсан бол дөрвөлжин хаалт байрлалаар ханддаг — гурван хаалт гурван өөр ажилтай болж байна. Гардуулагдаж буй зүйл нь нэг тэмдэгттэй string: ner[0] нь "Б" — Python-д "үсэг" гэсэн тусдаа төрөл байхгүй, ганц сувд ч гэсэн жижигхэн хэлхээ юм (тиймээс түүн дээр авдрын method-ууд ажиллана: ner[0].upper() бүрэн хууль ёсны). Тэгээд нэг чухал тулгалт: хамгийн сүүлчийн индекс нь len - 1: "Бат" гурван урттай, сүүлчийн индекс нь 2. Урт ба сүүлчийн индексийн энэ "нэгийн зөрөө" бол 0-тооллын үнэ бөгөөд яг энэ зөрөөн дээр өнөөдрийн гол алдаа амьдардаг — алдаануудын хэсэгт нүүр тулна.
Хоёр дахь жишээ: индекс ажилдаа — эхний үсгээр мэндлэх. Индексийг variable, f-string-тэй хоршуулъя:
python
ner = input("Таны нэр хэн бэ? ").strip()
ehnii = ner[0]
print(f"Таны нэрийн эхний үсэг: {ehnii}")
print(f"Томоор бол: {ehnii.upper()}")Оюунаа гэж хариулбал:
Таны нэрийн эхний үсэг: О
Томоор бол: ОИндексийн гардуулалт жирийн string тул хайрцганд хадгалагдаж (ehnii), нүхэнд суулгагдаж, авдрын багажаа дуудуулж байна — бүх хуучин мэдлэг шинэ бичиглэлтэй шууд гар нийлэв. Input-ын ард .strip() залгагдсаныг ажигла — өмнөх хичээлүүдийн "угаалгын" дадал энд амин чухал боллоо: хэрэглэгч урдаа зай дарсан бол ner[0] нь үсэг биш зай гарч ирэх байсан (зай ч тэмдэгт мөн — индекст ч тоологдоно!). Индекстэй ажиллахын өмнө string-ээ цэвэрлэх нь мэргэжлийн зан үйл.
Гурав дахь жишээ: сөрөг индекс — арын хаалга. Сүүлчийн тэмдэгтийг авъя гэвэл len - 1 тооцоо хийх үү? Болно — гэхдээ Python нэг тансаг товчлол өгдөг: сөрөг индекс — арын үзүүрээс тоолдог:
python
ug = "Улаанбаатар"
print(ug[-1])
print(ug[-2])
print(ug[len(ug) - 1])Үр дүн:
р
а
рug[-1] — "арын үзүүрээс эхний" буюу сүүлчийн тэмдэгт; ug[-2] — сүүлчээсээ өмнөх. Гурав дахь мөр нь -1-ийн "урт зам" хувилбар: len(ug) - 1 = 10 индекс — мөн л "р": хоёр зам нэг сувдад хүрч байгааг тулгаж үзүүлэв — сөрөг индекс бол шинэ ид шид биш, тооцооны товчлол юм. Сөрөг талд тоолол -1-ээс эхэлдгийг ажигла (0-ээс биш: -0 гэдэг нь 0-тэйгээ адилхан тул "арын эхлэл" -1 байхаас өөр аргагүй). Өдөр тутмын хэрэглээнд -1, -2 хоёроос цааш ховор явдаг — "сүүлчийнх нь юу вэ" гэсэн асуулт л хамгийн түгээмэл: файлын нэрний сүүлчийн үсэг, дугаарын сүүлчийн цифр...
Дөрөв дэх жишээ: индекс + loop — хэлхээгээр алхах. Индекс range-тэй гар нийлэхээр string-ийн тэмдэгт бүр дээр очиж болно:
python
ug = "Бат"
for i in range(len(ug)):
print(f"Индекс {i}: {ug[i]}")Үр дүн:
Индекс 0: Б
Индекс 1: а
Индекс 2: тrange(len(ug)) — зүйрлэлийн хэсэгт дурдсан тэр "барьцалдсан" хэв маяг: len нь 3 тул range нь 0, 1, 2 — яг гурван хүчинтэй индекс, нэг ч дутуугүй, нэг ч илүүгүй: 0-тооллын шагнал энэ мөрөнд бүрэн харагдана. Тойрог бүрд i индексийн тэмдэгтийг ug[i]-ээр сугалж хэвлэв — string-ээр "алхах" анхны туршлага. Нэг үнэнч тэмдэглэл: string-ийн тэмдэгт бүр дээр очих илүү богино зам Python-д бий (for usg in ug: — индексгүйгээр шууд) бөгөөд бид түүнийг дараагийн бүлгийн "List ба for loop хамтдаа" хичээлд ёсоор нь үзнэ; өнөөдрийн range(len(...)) хэлбэр нь "индекс нь өөрөө хэрэгтэй" үед (дугаарыг нь хамт хэвлэх гэх мэт) хэрэглэгддэг хувилбар нь юм.
Тав дахь жишээ: индексээр шалгалт хийх. Жижигхэн бодит хэрэглээ — регистрийн эхний үсгээр хүйс таамагладаг систем биш ээ — нэрний эхний, сүүлчийн үсгийг харьцуулж "тэгш хэмтэй" эсэхийг шалгая:
python
ner = input("Нэг үг бичээрэй: ").strip().lower()
if ner[0] == ner[-1]:
print(f"Сонирхолтой: {ner} гэдэг үгийн эхний ба сүүлчийн үсэг ижил!")
else:
print(f"Эхнийх нь {ner[0]}, сүүлчийнх нь {ner[-1]} — өөр байна.")наран гэж бичвэл "эхний ба сүүлчийн үсэг ижил!" гарна (н...н). Индексүүд харьцуулалтын жинлүүр дээр шууд тавигдаж байгааг ажигла — ner[0] ner[-1] гэдэг нь хоёр нэг-тэмдэгтийн string-ийн тулгалт: бүх хуучин дүрэм ( нь string дээр тэмдэгт бүрээр тулгадаг) хүчинтэй. Мөн .strip().lower() угаалга энд хоёр үүрэг гүйцэтгэж байна: захын зай индексийг "эзлэхээс" сэргийлж, Наран/наран хоёрын н/Н зөрөхөөс хамгаалж байна — өмнөх хоёр хичээлийн дадал шинэ сэдэвтэй сүлжилдэн ажиллаж байгааг харж байна уу.
Хүсвэл туршаад үзээрэй: өөрийн нэрний эхний болон сүүлчийн үсгийг f-string-ээр нэг өгүүлбэрт багтаан хэвлээрэй. Сонирхвол дөрөв дэх жишээний loop-ыг ухраагаад үзээрэй — range(len(ug) - 1, -1, -1) (ухраах range-ийн гурван орц: сүүлчийн индексээс, -1-д хүрэлгүй буюу 0 хүртэл, нэг нэгээр буурч) — үгээ урвуугаар нь хэвлэдэг loop гарна: "тэгш хэмтэй үг" (наран!) шалгагчийн эхлэл эндээс харагдана.
Алдаа 1: Хэлхээнээс халих — IndexError. Өнөөдрийн шинэ танил алдаа, "нэгийн зөрөөний" үр удам:
python
ner = "Бат"
print(ner[3])Python:
IndexError: string index out of rangeОрчуулбал: "IndexError (индексийн алдаа): string-ийн индекс хүрээнээс халив." "Бат" гурван урттай — "гуравтай юм чинь [3] байлгүй дээ" гэсэн зөн совин яг энд бүдэрдэг: индексүүд нь 0, 1, 2 — [3] гэдэг сувд байхгүй: гурав дахь байшин эхлэлээс хоёр алхам зайтай шүү дээ. Энэ бол off-by-one-ы индекс-хувилбар бөгөөд хамгийн олон гардаг дүр нь: ner[len(ner)] — "уртаар нь индекслэх" (зөв нь len - 1 эсвэл шууд -1). Range-тэй нэг гоё зэрэгцүүлэл: range-ийн зогсоол "орохгүй" байсан шиг len дугаар "байхгүй" — хоёулаа нэг зоосны хоёр тал: хүчинтэй индексийн дээд хязгаар = урт хасах нэг. IndexError гарвал оношлогооны хоёр алхам: string-ийнхээ уртыг len-ээр хэвлэ, индексээ түүнтэй тулга — халилт үргэлж тэндээс олдоно. (Сөрөг талдаа ч халиж болно: ner[-4] мөн ижил IndexError.)
Алдаа 2: Хоосон string-ийн [0] — халилтын далд хувилбар. Хамгийн зальтай IndexError:
python
ner = input("Таны нэр хэн бэ? ").strip()
print(f"Эхний үсэг: {ner[0]}")Хэрэглэгч юу ч бичилгүй Enter дарвал (эсвэл зөвхөн зай дараад strip-д "иддүүлбэл"): IndexError: string index out of range. Хоосон string тэг урттай — [0] индекс хүртэл байхгүй: нэг ч байшингүй гудамжинд "эхний байшин" гэж асуусан хэрэг. Энэ алдааны аюул нь заримдаа л гардагт: та туршихдаа үргэлж нэрээ бичдэг тул программ "ажилладаг" — харин бодит хэрэглэгч хоосон Enter дармагц унана: input()-ын хичээлийн "гадны ертөнцөөс ирж буй мэдээлэл найдваргүй" сургамжийн индекс-дүр. Хамгаалалт нь танил хэрэгсэл — len ба if: if len(ner) == 0: гэж эхэнд нь шүүгээд (эрт буцах/continue хэв маяг!) анхааруулга өгч дахин асуувал программ "тэсвэртэй" болно. Дүрэм: [0]-д хүрэхийн өмнө хоосон биш гэдгийг шалга — ялангуяа орц нь хэрэглэгчээс ирж байвал.
Алдаа 3: Индексээр тэмдэгт солих гэж оролдох. Хэлхээний сувдыг "суйлж" болдог юм чинь "сольж" бас болох байх гэсэн зөн совин:
python
ner = "бат"
ner[0] = "Б"Python:
TypeError: 'str' object does not support item assignmentОрчуулбал: "str төрөл гишүүн-оноолтыг дэмждэггүй" — string-ийн дотор нь оноолт хийж болохгүй гэсэн үг. Энэ бол санамсаргүй хязгаар биш — string-ийн мөн чанар: Python-д string үл өөрчлөгдөх (immutable) төрөл юм. Танил дуулиа биз: өмнөх хичээлд "method-ууд эх string-ээ хэзээ ч өөрчилдөггүй — шинийг гардуулдаг" гэж дахин дахин хэлсэн — одоо учир нь ил боллоо: string-ийг өөрчлөх ямар ч зам угаасаа байхгүй учраас method-ууд шинийг гардуулахаас өөр сонголтгүй байжээ. "Тэгвэл эхний үсгийг нь яаж томруулах юм бэ?" — шинийг барина: ner = ner[0].upper() + ner[1:]... болиод — тэр [1:] гэсэн сониуч бичиглэл (хэлхээний "хэсгийг" авдаг slice гэдэг чадвар) бол энэ сургалтын хүрээнээс гадуурх амттан — энгийн зам нь: ner = ner.replace("б", "Б", 1)... үүн дээр ч гурав дахь argument гэсэн шинэ юм гарлаа — за хамгийн энгийнээр: ner = "Б" + ner.replace("б", "", 1) ч гэж болно, гэхдээ хамгийн зөв хариулт нь: эхний үсэг томруулдаг бэлэн method string-ийн авдарт байдаг — ner.capitalize() — сонирхвол туршаад үзээрэй. Гол сургамж нь бичиглэлийн жор биш: string уншигдана, өөрчлөгдөхгүй — "өөрчлөлт" бол үргэлж шинэ string барьж дарж хадгалах явдал. Харин дараагийн бүлгийн list — тэр чинь өөрчлөгддөг цуглуулга: ner[0] = "Б" маягийн оноолт тэнд бүрэн хууль ёсны болно — энэ ялгаа хоёр төрлийн хамгийн гүн зааг юм.
Индекс бол "хэд дэх" биш "эхлэлээс хэр зайтай" — тиймээс эхний тэмдэгт 0, сүүлчийнх нь len - 1: ner[0], ner[len(ner) - 1].
Дөрвөлжин хаалт бол байрлалаар хандах гурав дахь "дуудлагын хэлбэр" (дугуй — function, цэг — авдар); гардуулалт нь нэг тэмдэгттэй жирийн string.
Сөрөг индекс арын үзүүрээс тоолно: [-1] — сүүлчийнх, [-2] — түүний өмнөх; -1-ээс эхэлдэг.
Байхгүй индекст хандвал IndexError: string index out of range — уртаа len-ээр шалгаж тулга; хоосон string-ийн [0] бол далд халилт: хэрэглэгчийн орцод len == 0 шүүлт тавь.
String үл өөрчлөгдөнө: ner[0] = "Б" нь TypeError — "өөрчлөлт" бол шинэ string барьж дарж хадгалах; өөрчлөгддөг цуглуулга бол дараагийн бүлгийн list.
Ингээд String гүнзгийрүүлэх бүлэг өндөрлөлөө — дугтуй маань авдартай, нүхтэй, дугаартай болж дууслаа. Дараагийн бүлэг бол Түвшин 2-ын сүүлчийн, хамгийн том материал: List ба Dictionary — олон утгыг нэг дор тээдэг цуглуулгууд. Split-ийн гардуулж байсан тэр дөрвөлжин хаалттай сав, "олон утга гардуулах" бодлогын хариулт, gerchilgee-г loop-оор дуудах мөрөөдөл, тэгээд өнөөдрийн "өөрчлөгддөг [0] = ..." оноолт — бүгд тэнд биеллээ олно. Индексийн мэдлэг чинь тэнд шууд, бүрэн дүүрэн ажилд орно: list ч мөн 0-ээс тоолдог хэлхээ юм.
Бүртгэлтэй болсноор энэ сургалтын бүх хичээлд хандах эрх авна.