- ndarray-in atributlarını (
ndim,shape,size,dtype) izah etmək və massivin yaddaş həcmini hesablamaq arange,linspace,zerosvə toxumludefault_rngilə massivlər yaratmaq- İndeks, kəsik və məntiqi maskalarla verilənləri seçmək, görünüşü surətdən fərqləndirmək
axisparametri ilə sətir və sütunlar üzrə statistik göstəriciləri hesablamaq
Hava stansiyası il boyu hər saat temperaturu ölçür — bu, 8760 ədəd deməkdir. Onların orta qiymətini, ən isti günləri və aylıq ortaları adi Python siyahıları və dövrlərlə də hesablamaq olar, amma yavaş və uzun kodla. NumPy (Numerical Python) eyni işi bir sətirlə və dəfələrlə sürətli görür. pandas, matplotlib, SciPy, scikit-learn — Python-da verilənlər elminin bütün alətləri NumPy massivləri üzərində qurulub, ona görə bu modul məhz ondan başlayır.
NumPy-ın əsas obyekti: eyni tipli elementlərdən ibarət, ölçüsü sabit olan çoxölçülü cədvəl. Elementlər yaddaşda bir-birinin ardınca yerləşir, əməliyyatlar isə kompilyasiya olunmuş C kodunda bütün massiv üzərində birdən icra olunur.
ndarray: forma, ölçü və tip
Python siyahısı hər elementi ayrıca obyekt kimi saxlayır və özündə yalnız onlara göstəriciləri (ünvanları) tutur, massiv isə «xam» ədədləri bir blokda saxlayır. Buna görə massiv həm az yer tutur, həm də sürətli emal olunur. Hər massivin dörd əsas atributu var: ndim — ölçülərin (oxların) sayı, shape — hər ox üzrə uzunluqlardan ibarət kortej, size — elementlərin ümumi sayı, dtype — elementlərin tipi.
import numpy as np
temps = np.array([12.5, 14.0, 9.8, 11.2])
print(temps)
print(temps.ndim, temps.shape, temps.size, temps.dtype)
print(temps.itemsize, temps.nbytes)
m = np.array([[1, 2, 3], [4, 5, 6]])
print(m)
print(m.ndim, m.shape, m.size)
print(m * 10)▸ Gözlənilən nəticə
[12.5 14. 9.8 11.2] 1 (4,) 4 float64 8 32 [[1 2 3] [4 5 6]] 2 (2, 3) 6 [[10 20 30] [40 50 60]]
m * 10 dövrsüz işləyir: əməl hər elementə tətbiq olunur. Siyahıda isə [1, 2] * 10 siyahını 10 dəfə təkrarlayardı.- noxların sayı (
ndim) - dₖk-cı ox üzrə uzunluq (
shape-in elementi) - itemsizebir elementin bayt ilə ölçüsü:
float64vəint64üçün 8,float32vəint32üçün 4,boolvəint8üçün 1
Forması (2, 3) olan m üçün size = 2 · 3 = 6. temps üçün nbytes = 4 · 8 = 32 bayt.
| dtype | Bayt | Diapazon / dəqiqlik | Harada işlənir |
|---|---|---|---|
bool | 1 | True / False | maskalar, bayraqlar |
uint8 | 1 | 0 … 255 | şəkil pikselləri |
int32 | 4 | təxminən ±2,1 · 10⁹ | sayğaclar, indekslər |
int64 | 8 | təxminən ±9,2 · 10¹⁸ | böyük tam ədədlər |
float32 | 4 | ~7 əhəmiyyətli rəqəm | neyron şəbəkələr, GPU |
float64 | 8 | ~15–16 əhəmiyyətli rəqəm | kəsr ədədlər üçün susmaya görə tip |
Massivin bütün elementləri eyni tipdə olmalıdır. Müxtəlif tiplər qarışanda NumPy hamısını «ən geniş» tipə çevirir: tam ədəd və kəsr birlikdə float64 verir, ədəd və sətir birlikdə — sətir. astype tipi açıq şəkildə dəyişir; kəsrdən tama çevirəndə kəsr hissə yuvarlaqlaşdırılmır, sadəcə atılır.
import numpy as np
print(np.array([1, 2, 3.5]))
print(np.array([1, 2, '3']))
print(np.array([1.9, -1.9]).astype(np.int32))
small = np.array([100, 120], dtype=np.int8)
print(small + small)▸ Gözlənilən nəticə
[1. 2. 3.5] ['1' '2' '3'] [ 1 -1] [-56 -16]
Massivlərin yaradılması
| Funksiya | Nə yaradır |
|---|---|
np.array(data) | siyahıdan və ya iç-içə siyahılardan massiv |
np.zeros(shape), np.ones(shape), np.full(shape, v) | 0, 1 və ya v ilə doldurulmuş massiv |
np.arange(start, stop, step) | range kimi addımlı ardıcıllıq; stop daxil deyil |
np.linspace(start, stop, num) | bərabər aralıqlı num nöqtə; hər iki uc daxildir |
np.eye(n) | n × n vahid matris |
np.random.default_rng(seed) | təsadüfi ədədlər generatoru |
import numpy as np
print(np.zeros((2, 3)))
print(np.arange(0, 10, 2))
print(np.linspace(0, 1, 5))
print(np.full(3, 7.5))
print(np.eye(3))▸ Gözlənilən nəticə
[[0. 0. 0.] [0. 0. 0.]] [0 2 4 6 8] [0. 0.25 0.5 0.75 1. ] [7.5 7.5 7.5] [[1. 0. 0.] [0. 1. 0.] [0. 0. 1.]]
- h
linspacenöqtələri arasındakı addım - n
arangemassivindəki elementlərin sayı - ⌈ ⌉yuxarı yuvarlaqlaşdırma
np.linspace(0, 1, 5): h = 1 / 4 = 0,25. np.arange(0, 10, 2): n = ⌈10 / 2⌉ = 5 element.
Kəsr addımlı arange ilə ehtiyatlı ol: 0,1 ikilik sistemdə dəqiq göstərilə bilmir və yuvarlaqlaşdırma xətası son elementin massivə düşüb-düşməməsini dəyişə bilər. Aşağıda stop = 1.3 olsa da, 1,3 massivə daxil olub:
import numpy as np
print(np.arange(0, 1, 0.1).size)
print(np.arange(1, 1.3, 0.1))
print(np.linspace(1, 1.3, 4))▸ Gözlənilən nəticə
10 [1. 1.1 1.2 1.3] [1. 1.1 1.2 1.3]
Təsadüfi ədədlər üçün müasir yol generator yaratmaqdır: rng = np.random.default_rng(42). Burada 42 toxumdur (seed): eyni toxumla generator hər dəfə eyni ardıcıllığı verir. Bu, elmi işdə vacibdir — həmkarın sənin kodunu işə salıb eyni nəticəni ala bilməlidir. integers(a, b) yuxarı sərhədi daxil etmir, normal(loc, scale) normal paylanmadan, random() isə [0; 1) aralığından ədədlər qaytarır. Köhnə kodlarda görəcəyin np.random.seed və np.random.rand əvəzinə yeni kodda generatordan istifadə et.
import numpy as np
rng = np.random.default_rng(42)
print(rng.integers(1, 7, size=10))
print(rng.normal(loc=170, scale=8, size=4).round(1))
print(rng.random((2, 3)).round(3))▸ Gözlənilən nəticə
[1 5 4 3 3 6 1 5 2 1] [159.6 171. 167.5 169.9] [[0.45 0.371 0.927] [0.644 0.823 0.443]]
İndeksləmə, kəsiklər və məntiqi maskalar
Birölçülü massiv siyahı kimi indekslənir: a[0], a[-1], a[2:5], a[::2]. İkiölçülü massivdə indekslər vergüllə ayrılır: m[sətir, sütun]. İki nöqtə : «bu ox üzrə hamısı» deməkdir: m[:, 1] — ikinci sütun, m[1] — ikinci sətir. Kəsiklər hər ox üzrə ayrıca işləyir, mənfi addım isə sıranı tərsinə çevirir.
import numpy as np
m = np.arange(1, 13).reshape(3, 4)
print(m)
print(m[1, 2], m[-1, -1])
print(m[:, 1])
print(m[0:2, 1:3])
print(m[::2, ::-1])▸ Gözlənilən nəticə
[[ 1 2 3 4] [ 5 6 7 8] [ 9 10 11 12]] 7 12 [ 2 6 10] [[2 3] [6 7]] [[ 4 3 2 1] [12 11 10 9]]
reshape(3, 4) 12 elementi 3 sətir və 4 sütuna düzür (növbəti dərsdə ətraflı). m[::2, ::-1] — hər ikinci sətir, sütunlar tərs sırada.import numpy as np
m = np.arange(1, 13).reshape(3, 4)
row = m[0]
row[0] = 100
print(m[0])
safe = m[1].copy()
safe[0] = -1
print(m[1], safe)▸ Gözlənilən nəticə
[100 2 3 4] [5 6 7 8] [-1 6 7 8]
Müqayisə operatoru massivə tətbiq olunanda hər element üçün True və ya False qaytarır — bu, məntiqi maskadır. Maskanı indeks kimi versən, yalnız True olan elementlər seçilir. True 1, False isə 0 kimi hesablandığından mask.sum() şərtə uyğun elementlərin sayını, mask.mean() isə onların payını verir. np.where(şərt, a, b) hər element üçün «əgər…, onda a, yoxsa b» seçimini bir əməldə edir. Aşağıda bir həftənin günorta temperaturları var:
import numpy as np
temps = np.array([21.4, 25.8, 31.2, 28.9, 33.5, 26.1, 19.7])
hot = temps > 28
print(hot)
print(temps[hot])
print(np.flatnonzero(hot))
print(hot.sum(), 'hot days,', f'{hot.mean():.0%} of the week')
print(temps[(temps > 20) & (temps < 27)])
print(np.where(temps > 30, 30.0, temps))▸ Gözlənilən nəticə
[False False True True True False False] [31.2 28.9 33.5] [2 3 4] 3 hot days, 43% of the week [21.4 25.8 26.1] [21.4 25.8 30. 28.9 30. 26.1 19.7]
np.flatnonzero True olan elementlərin indekslərini qaytarır: 0-dan saydıqda 2, 3 və 4 nömrəli günlər. Sonuncu sətir 30-dan yuxarı qiymətləri 30 ilə əvəz edir.a = np.arange(12).reshape(3, 4) üçün kodu işə salmadan tap: a) a[1:, ::2]; b) a.sum(axis=0) və a.sum(axis=1) və onların formaları; c) (a % 5 == 0).sum().
Həllini göstərHəllini gizlət
a)
1: — 1 və 2 nömrəli sətirlər, ::2 — 0 və 2 nömrəli sütunlar: [[4 6], [8 10]].b) axis=0 sətirləri «sıxır», hər sütunun cəmi qalır: [0+4+8, 1+5+9, 2+6+10, 3+7+11] = [12 15 18 21], forma (4,).
axis=1 hər sətrin cəmini verir: [6 22 38], forma (3,).
c) 5-ə bölünən elementlər 0, 5 və 10-dur, maskada 3 dənə
True var: cavab 3.Aqreqasiya və axis parametri
sum, mean, min, max, std, argmax, cumsum kimi funksiyalar çoxlu ədədi bir ədədə və ya daha kiçik massivə «yığır» — buna aqreqasiya deyilir. axis verilməsə, hesablama bütün massiv üzrə aparılır. axis=0 birinci ox (sətirlər) boyunca hesablayır və hər sütun üçün bir nəticə verir; axis=1 sütunlar boyunca hesablayır və hər sətir üçün bir nəticə verir. Aşağıda 4 tələbənin (sətirlər) riyaziyyat, fizika və kimyadan (sütunlar) balları var:
import numpy as np
scores = np.array([[85, 92, 78],
[67, 74, 81],
[93, 88, 95],
[72, 65, 70]])
print(scores.shape, scores.sum())
print(scores.mean(axis=0))
print(scores.mean(axis=1).round(2))
print(scores.max(axis=0), scores.argmax(axis=0))
print(scores.std(axis=0).round(2))
print(scores.std(axis=0, ddof=1).round(2))
print(scores.cumsum(axis=1)[0])▸ Gözlənilən nəticə
(4, 3) 960 [79.25 79.75 81. ] [85. 74. 92. 69.] [93 92 95] [2 0 2] [10.3 10.83 9.03] [11.9 12.5 10.42] [ 85 177 255]
argmax(axis=0) hər fəndə ən yaxşı tələbənin indeksini verir: riyaziyyat və kimyada 2 nömrəli, fizikada 0 nömrəli.- x̄ədədi orta (
mean) - nqiymətlərin sayı
- σstandart meyl (
std), qiymətlərin ortadan orta hesabla nə qədər uzaqlaşdığı - ddof0 — baş məcmu üçün (NumPy-da susmaya görə), 1 — seçmə üçün (sürüşməsiz dispersiya)
np.std susmaya görə n-ə bölür, statistika dərslikləri və pandas-dakı Series.std isə n − 1-ə. Eyni nəticə üçün ddof=1 ötür.
x = [2, 4, 4, 4, 5, 5, 7, 9]. np.std(x) və np.std(x, ddof=1) nəyə bərabər olacaq?
Həllini göstərHəllini gizlət
Ortadan kənarlaşmaların kvadratları: 9, 1, 1, 1, 0, 0, 4, 16; cəmi 32.
ddof = 0: σ² = 32 / 8 = 4, σ = 2.
ddof = 1: s² = 32 / 7 ≈ 4,571, s ≈ 2,138.
n böyüdükcə iki cavab arasındakı fərq kiçilir.
Bu biliklər harada lazım olacaq? pandas cədvəllərinin sütunları NumPy massivləridir; scikit-learn verilənləri (n × d) formalı massiv kimi qəbul edir; şəkillərin emalı, siqnallar, maliyyə sıraları və fizika modelləri — hamısı massivlər üzərində əməliyyatlardır. Növbəti dərsdə dövrləri tamamilə vektorlaşdırılmış kodla əvəz etməyi və xətti cəbri öyrənəcəksən.
sales massivində kiçik kafenin 4 həftəlik satışları var (sətirlər — həftələr, sütunlar — bazar ertəsindən bazara qədər günlər). Ayrı-ayrı sətirlərdə çap et: 1) hər həftənin ümumi satışı; 2) 4 həftə üzrə ən çox satış olan həftə gününün indeksi (0 = bazar ertəsi); 3) satışın 100-dən çox olduğu günlərin sayı. Dövr işlətmə.
import numpy as np
sales = np.array([[80, 95, 110, 90, 130, 150, 70],
[85, 100, 105, 95, 140, 160, 75],
[90, 92, 120, 88, 125, 155, 80],
[78, 99, 115, 97, 135, 165, 72]])
# 1) total per week
# 2) index of the best weekday
# 3) number of days above 100▸ Gözlənilən nəticə
[725 760 750 761] 5 12
Sensorun ölçmələrində mənfi qiymətlər xətadır. 1) np.where ilə mənfi qiymətləri 0.0 ilə əvəz edib yeni massivi çap et; 2) ilkin massivdə 10-dan böyük ölçmələrin ortasını 1 onluq rəqəmə qədər yuvarlaqlaşdırıb çap et.
import numpy as np
readings = np.array([12.5, -3.0, 8.4, 15.1, -1.2, 20.3, 9.9, 11.0])
# 1) negatives -> 0.0
# 2) mean of readings > 10, rounded to 1 decimal▸ Gözlənilən nəticə
[12.5 0. 8.4 15.1 0. 20.3 9.9 11. ] 14.7
Əsas fikirlər
- ndarray eyni tipli elementləri yaddaşda ardıcıl saxlayır; əsas atributları
ndim,shape,size,dtype-dır, nbytes = size · itemsize. arangestop-u daxil etmir; kəsr addım üçün hər iki ucu daxil edənlinspacedaha etibarlıdır.- Təkrarlana bilən təsadüfi ədədlər üçün
np.random.default_rng(seed)generatorundan istifadə et. - Kəsik görünüşdür: onu dəyişmək əsl massivi dəyişir; müstəqil surət üçün
.copy(). - Maskaları
&,|,~və mötərizələrlə birləşdir;mask.sum()say,mask.mean()pay verir. axis=kk oxunu nəticənin formasından çıxarır;np.stdsusmaya görəddof=0işlədir.
Özünü yoxla
10 sual. Hər düzgün cavab XP qazandırır.
np.zeros((3, 4)).sum(axis=0) nəticəsinin forması nədir?