Înapoi la catalog
Season 35 8 Episoade 32 min 2026

Mastering Modern Pandas

v3.0 — Ediția 2026. Stăpânește abstracțiile de bază și capabilitățile moderne ale pandas 3.0 în 2026. Învață despre alinierea datelor, Copy-on-Write, integrarea PyArrow, stăpânirea seriilor de timp și strategii pentru scalarea seturilor de date out-of-core.

Știința datelor Analiza datelor Python Core
Mastering Modern Pandas
Se redă acum
Click play to start
0:00
0:00
1
Abstracția de bază: DataFrames și alinierea etichetelor
Explorăm modelele mentale fundamentale din pandas: Series și DataFrame. Vei învăța de ce alinierea intrinsecă a etichetelor este funcționalitatea esențială care previne dezastrele cauzate de nepotrivirea rândurilor.
4m 11s
2
Revoluția Copy-on-Write
Descoperă cea mai semnificativă schimbare arhitecturală din pandas modern: Copy-on-Write. Vei învăța cum CoW elimină mutațiile imprevizibile și optimizează utilizarea memoriei.
4m 23s
3
Motorul PyArrow
Pandas nu mai este susținut doar de NumPy. Vei învăța cum să folosești backend-ul PyArrow pentru suport nativ al datelor lipsă și economii incredibile de memorie pentru șirurile de caractere.
3m 44s
4
Ingestia modernă a datelor
Abordăm strategii I/O eficiente pentru seturi mari de date. Vei învăța cum să faci ingestia fișierelor masive în mod selectiv și direct în structuri de memorie extrem de optimizate.
3m 42s
5
Algebră relațională: Merge și Join
Explorăm cum să unificăm seturi de date disparate folosind algebra relațională. Vei învăța să execuți join-uri optimizate în stil SQL direct în pandas.
4m 05s
6
Șablonul Split-Apply-Combine
Deblochează adevărata putere a obiectului GroupBy. Vei învăța cum să treci dincolo de mediile simple pentru a efectua transformări și filtrări complexe specifice grupurilor.
3m 45s
7
Stăpânirea seriilor de timp
Ne scufundăm în dominația incontestabilă a pandas în analiza seriilor de timp. Vei învăța cum să folosești DatetimeIndex și funcția nativă de resampling pentru date de înaltă frecvență.
4m 34s
8
Scalarea la seturi de date Out-of-Core
Abordăm limitele memoriei RAM a mașinii tale. Vei învăța cum să procesezi seturi de date semnificativ mai mari decât memoria folosind exclusiv chunking în pandas.
4m 29s

Episoade

1

Abstracția de bază: DataFrames și alinierea etichetelor

4m 11s

Explorăm modelele mentale fundamentale din pandas: Series și DataFrame. Vei învăța de ce alinierea intrinsecă a etichetelor este funcționalitatea esențială care previne dezastrele cauzate de nepotrivirea rândurilor.

Descarcă
Salut, sunt Alex de la DEV STORIES DOT EU. Mastering Modern Pandas, episodul 1 din 8. Extragi două coloane de date financiare, le aduni, iar suma finală nu are sens. Rândurile s-au decalat, iar tu tocmai ai adunat prețul de închidere de ieri cu volumul de astăzi. Asta se întâmplă atunci când tratezi datele ca pe o grilă banală, în loc să te bazezi pe Abstractizarea de Bază: DataFrames și Label Alignment. Oamenii se uită adesea la pandas și cred că este doar un spreadsheet programatic sau un array NumPy bidimensional standard. Nu e așa. Un array NumPy simplu se bazează pe o indexare pozițională strictă. Dacă aduni două array-uri, elementul de la poziția zero se adună cu elementul de la poziția zero. Dacă din datele tale lipsește un rând, totul se decalează, iar calculele tale sunt corupte silențios. Pandas rezolvă exact această problemă prin decuplarea datelor de poziția lor fizică în memorie. Folosește alinierea intrinsecă a datelor, adică aliniază datele după labels, niciodată după poziție. Pentru a înțelege asta, uită-te la fundația librăriei, obiectul Series. Un Series este un array unidimensional care poate conține orice tip de date. Spre deosebire de o listă standard, fiecare element dintr-un Series este atașat ferm de un label. Aceste labels formează colectiv ceea ce pandas numește index. Poți folosi integeri ca labels, dar, mai des, folosești string-uri sau timestamp-uri. Un DataFrame este pur și simplu o colecție de astfel de obiecte Series care funcționează ca niște coloane, toate partajând același index, așezate una lângă alta. Iată ideea cheie. Când faci o operațiune în pandas, indexul dictează comportamentul. Să zicem că ai două obiecte Series cu randamentele zilnice ale unor acțiuni. Series A are date pentru luni, marți, miercuri și joi. Series B are date pentru miercuri, joi și vineri. Dacă îi dai comandă lui pandas să adune aceste două obiecte Series, va ignora ordinea lor fizică. Se uită la acele labels de dată. Găsește ziua de miercuri în Series A și o adună cu ziua de miercuri din Series B, chiar dacă miercuri este al treilea element din primul dataset și primul element din al doilea dataset. Acest lucru aduce în discuție problema zilelor care nu se suprapun. Luni există în primul Series, dar nu și în al doilea. Vineri există în al doilea, dar nu și în primul. Pandas nu dă crash și cu siguranță nu ghicește o valoare. În schimb, creează un nou index care este uniunea tuturor acelor labels din ambele input-uri. Pentru orice label care nu există în ambele locuri, pandas inserează un NaN, adică Not a Number. Operațiunea se finalizează cu succes și poți vedea imediat unde datele tale sunt incomplete. Nu trebuie niciodată să scrii un loop pentru a verifica dacă datele se potrivesc. Alinierea este automată, încorporată direct în însăși structura de date. Aceeași logică se scalează direct la DataFrame-uri. Un DataFrame se aliniază simultan pe ambele dimensiuni. Când operezi pe două DataFrame-uri, pandas potrivește label-ul rândului cu label-ul rândului, și numele coloanei cu numele coloanei. Aliniază perfect întreaga structură înainte de a executa o singură operațiune matematică. Orice nu se suprapune atât pe rânduri, cât și pe coloane este marcat ca date lipsă. Adevărata putere a librăriei pandas nu constă în calculele pe care le face, ci în faptul că acel label călătorește întotdeauna odată cu datele, făcând nepotrivirile poziționale imposibile din punct de vedere structural. Dacă vrei să susții emisiunea, ne poți găsi căutând DevStoriesEU pe Patreon. Mulțumesc pentru audiție, happy coding tuturor!
2

Revoluția Copy-on-Write

4m 23s

Descoperă cea mai semnificativă schimbare arhitecturală din pandas modern: Copy-on-Write. Vei învăța cum CoW elimină mutațiile imprevizibile și optimizează utilizarea memoriei.

Descarcă
Salut, sunt Alex de la DEV STORIES DOT EU. Mastering Modern Pandas, episodul 2 din 8. Extragi un slice din datele tale, actualizezi o singură valoare și, dintr-o dată, dataset-ul original este corupt. Sau, mai rău, primești un warning imprevizibil și nu ai nicio idee dacă update-ul s-a aplicat de fapt pe slice sau pe sursă. Versiunea 3.0 rezolvă în sfârșit acest haos, setând Copy-on-Write drept comportament default. Copy-on-Write rescrie fundamental modul în care pandas gestionează memoria. În versiunile anterioare, pandas făcea frecvent copii defensive pentru a te împiedica să modifici accidental dataset-ul original. Dacă filtrai un dataset, pandas îl copia. Dacă făceai drop la o coloană, pandas copia restul. Asta irosea cantități masive de memorie și cicluri de CPU. Când nu copia, returna un view, ceea ce însemna că modificarea noului obiect altera în tăcere părintele. Cu Copy-on-Write, orice DataFrame sau Series derivat din altul împarte exact aceeași memorie underlying. Asta înseamnă că extragerea unui subset, un drop pe o coloană sau un reset de index se fac aproape instantaneu. Datele nu sunt duplicate upfront. Iată ideea cheie. Nu confunda un legacy view cu un lazy copy din Copy-on-Write. Într-un view tradițional, atât părintele, cât și copilul pointează către aceeași memorie, iar o modificare adusă unuia îl modifică și pe celălalt. Copy-on-Write este diferit. Memoria partajată este temporară și strict protejată. Partajarea durează doar până când încerci să schimbi ceva. Ia în considerare un scenariu concret. Ai un DataFrame care conține profiluri de utilizatori. Selectezi coloana age și o atribui unei noi variabile numite age subset. În acest moment exact, age subset ocupă zero memorie în plus. Pointează direct către DataFrame-ul original cu profilurile de utilizatori. Apoi, actualizezi prima valoare din age subset la nouăzeci și nouă. Aici intervine partea de write din Copy-on-Write. pandas detectează modificarea. Înainte să execute update-ul, verifică dacă vreun alt obiect partajează acest bloc specific de date. Pentru că DataFrame-ul părinte încă îl folosește, pandas alocă instantaneu memorie nouă, copiază datele, și apoi scrie valoarea nouăzeci și nouă în noua locație. DataFrame-ul părinte rămâne în siguranță, neschimbat. Modificarea unui subset nu alterează niciodată părintele. Acest mecanism se propagă perfect în cascadă prin chained operations. Când înlănțui operațiuni precum drop la rânduri goale, replace la valori și rename la coloane, versiunile mai vechi de pandas creau o copie fizică la fiecare pas. Cu Copy-on-Write, acești pași intermediari pur și simplu partajează memoria. O copie fizică este declanșată doar atunci când un pas modifică efectiv array-urile de date underlying. Dacă o operație doar rearanjează referințele, nu se face nicio copie. Asta elimină complet coruperea accidentală a datelor. Nu mai trebuie să ghicești dacă o operație a returnat un view sau o copie, și nu vei mai vedea niciodată warning-ul Setting With Copy. Regula este absolută: un obiect părinte și un obiect copil nu se vor modifica niciodată reciproc. Prin amânarea copiilor până în milisecunda exactă în care are loc o modificare, pandas îți oferă performanța rapidă și memory footprint-ul redus al view-urilor, combinate cu siguranța strictă a deep copies. Asta e tot pentru acest episod. Mulțumesc că ai ascultat și continuă să construiești!
3

Motorul PyArrow

3m 44s

Pandas nu mai este susținut doar de NumPy. Vei învăța cum să folosești backend-ul PyArrow pentru suport nativ al datelor lipsă și economii incredibile de memorie pentru șirurile de caractere.

Descarcă
Salut, sunt Alex de la DEV STORIES DOT EU. Mastering Modern Pandas, episodul 3 din 8. Încarci un dataset cu câteva milioane de rânduri și, dintr-o dată, utilizarea memoriei explodează. Numerele sunt în regulă, dar coloanele de text și acele missing values îți distrug în liniște memoria RAM. Soluția este o schimbare fundamentală în modul în care pandas stochează datele, și exact despre asta este vorba în acest episod: The PyArrow Engine Room. Dacă ai auzit de Apache Arrow, s-ar putea să crezi că este strict pentru sisteme distribuite mari, cum ar fi Spark sau Hadoop. Ei bine, nu e așa. Arrow este acum un memory format și un execution engine nativ, de primă clasă, direct în interiorul pandas. Ani de zile, pandas s-a bazat în întregime pe NumPy. NumPy este incredibil de rapid pentru calcule numerice dense, dar are un blind spot masiv în ceea ce privește missing data. NumPy nu are un concept nativ de missing integer sau missing boolean. Dacă ai o coloană de tip integer și ai un singur missing value, pandas a fost forțat istoric să convertească întreaga coloană în numere floating-point doar pentru a putea folosi markerul Not a Number. Asta îți modifică acele data types, strică acele exact matches și consumă mai multă memorie. PyArrow rezolvă asta folosind un validity bitmap. În loc să schimbe data type-ul pentru a acomoda un missing value, Arrow îți păstrează integer-urile ca integer-uri. Adaugă un array ascuns, extrem de comprimat, de unuri și zerouri alături de datele tale. Un unu înseamnă că valoarea este validă. Un zero înseamnă că este missing. Data type-ul tău rămâne intact, iar urmărirea acelor missing values costă aproape zero memorie. Iată ideea cheie. Economiile de memorie sunt și mai extreme atunci când lucrezi cu text. În mod tradițional, pandas stochează string-uri folosind data type-ul object din NumPy. Asta înseamnă că acea coloană nu conține de fapt textul tău. Conține memory pointers. Fiecare rând pointează către un obiect de tip string standard din Python, împrăștiat undeva prin memoria computerului tău. Dacă ai zece milioane de rânduri de text, ai zece milioane de pointeri și zece milioane de obiecte de tip string separate. Overhead-ul de memorie este uriaș, iar iterarea prin ele este teribil de lentă. PyArrow schimbă complet arhitectura. Când îți setezi coloanele pandas să folosească un data type de tip string din PyArrow, textul este stocat într-un singur bloc contiguu de memorie. Coloana doar ține evidența acelor byte offsets. Înregistrează exact unde începe și se termină fiecare cuvânt în acel bloc continuu mare. Imaginează-ți un dataset cu high-cardinality. Ai o coloană de user agent strings sau ID-uri unice de tranzacții. Multe dintre rânduri sunt goale. Dacă citești asta în pandas în mod tradițional, va face default la un object array din NumPy. Acum, spune-i lui pandas să folosească engine-ul PyArrow în schimb, atribuind explicit un string data type bazat pe PyArrow în timpul etapei de citire. Instant, memory footprint-ul scade, adesea cu cincizeci la sută sau mai mult. Îmbunătățirea depășește limitele de RAM. Deoarece datele sunt acum compactate strâns într-o structură construită pentru analytics, operațiunile de string matching se accelerează. Dacă rulezi o căutare cu regular expression pe acea coloană, engine-ul Arrow procesează acei raw bytes direct la nivel de sistem. Face bypass complet la overhead-ul lent al obiectelor Python. Obții coloane de tip integer care chiar rămân integer-uri atunci când ai missing data, și string operations care nu îți sufocă hardware-ul. Dacă procesezi text sau messy data, să te bazezi pe object array-ul din NumPy este complet depășit. Folosirea de data types bazate pe PyArrow este cea mai rapidă metodă de a face un pipeline pandas greoi instantaneu mai ușor. Mulțumesc pentru ascultare, happy coding tuturor!
4

Ingestia modernă a datelor

3m 42s

Abordăm strategii I/O eficiente pentru seturi mari de date. Vei învăța cum să faci ingestia fișierelor masive în mod selectiv și direct în structuri de memorie extrem de optimizate.

Descarcă
Salut, sunt Alex de la DEV STORIES DOT EU. Mastering Modern Pandas, episodul 4 din 8. Ai un fișier Parquet de mai mulți gigabytes cu o sută de coloane. Ai nevoie doar de patru dintre ele pentru a-ți rula metricile. Dacă prima ta mișcare este să încarci întregul fișier într-un dataframe și apoi să filtrezi coloanele, irosești cantități masive de RAM și cicluri de CPU înainte ca analiza ta măcar să înceapă. Soluția constă în stăpânirea Modern Data Ingestion. Principalul bottleneck în data ingestion este inputul și outputul pe disk. Funcțiile de read din Pandas, cum ar fi read underscore csv și read underscore parquet, scanează datele de pe disk în memorie. Pentru a minimiza acest transfer, folosești un argument numit usecols. Pasezi o listă care conține numele exacte ale coloanelor pe care le vrei. Parserul citește doar acele coloane specifice din fișier. Creșterea de performanță pe care o vezi depinde enorm de formatul fișierului tău. Fișierele CSV stochează datele rând cu rând. Când folosești usecols cu un CSV, parserul tot trebuie să scaneze întregul fișier text rând cu rând, dar elimină imediat coloanele de care nu ai nevoie înainte de a aloca memorie pentru dataframe. Fișierele Parquet, în schimb, stochează datele coloană cu coloană. Pentru un fișier Parquet cu o sută de coloane, unde ai nevoie doar de patru coloane de metrici, să pasezi usecols înseamnă că parserul ignoră complet blocurile din fișier care conțin celelalte nouăzeci și șase de coloane. Citește doar acei bytes de care are absolut nevoie de pe disk. Asta reduce drastic atât timpul de read, cât și memory footprint-ul. Restricționarea coloanelor este doar primul pas. Următoarea optimizare are loc în modul în care Pandas stochează acele coloane în memorie. Istoric vorbind, Pandas se baza în întregime pe array-uri NumPy. NumPy este excelent pentru calcul numeric dens, dar are probleme cu datele de tip text și cu missing values. Stochează string-urile ca obiecte Python dispersate în memorie și forțează coloanele de tip integer să devină float-uri doar pentru a reprezenta missing data. Pentru a rezolva asta, Pandas a introdus argumentul dtype backend. Când setezi acest argument la string-ul pyarrow, Pandas folosește Apache Arrow ca backend pentru datele tale. Arrow stochează string-urile în blocuri de memorie contigue, extrem de eficiente, și folosește un bitmask separat pentru a urmări missing values, păstrându-ți integer-urile intacte. Iată ideea cheie. S-ar putea să crezi că Pandas citește datele mai întâi în array-uri NumPy și apoi le convertește în Arrow. Nu asta se întâmplă. Când specifici backend-ul PyArrow în timpul funcției de read, Pandas face bypass complet la NumPy în timpul fazei de parse. Datele curg direct din fișierul de pe disk în array-urile PyArrow din memorie. Asta evită penalizarea severă de performanță a alocărilor intermediare de memorie. Hai să ne uităm la întregul pipeline. Apelezi read underscore parquet. Mai întâi, pasezi calea fișierului. În al doilea rând, pasezi usecols cu o listă a celor patru coloane de metrici. În al treilea rând, setezi argumentul dtype backend la pyarrow. Parserul sare direct la cele patru coloane de pe disk, le extrage și le face stream direct în memoria bazată pe Arrow. Ajungi să ai un dataframe suplu și extrem de rapid, care conține exact ceea ce ai nevoie, susținut de tipuri de date moderne. Filtrarea coloanelor la IO layer în loc de application layer este cea mai eficientă modalitate de a preveni crash-urile out-of-memory în Pandas. Asta e tot pentru acest episod. Mulțumesc pentru audiție și continuă să construiești!
5

Algebră relațională: Merge și Join

4m 05s

Explorăm cum să unificăm seturi de date disparate folosind algebra relațională. Vei învăța să execuți join-uri optimizate în stil SQL direct în pandas.

Descarcă
Salut, sunt Alex de la DEV STORIES DOT EU. Mastering Modern Pandas, episodul 5 din 8. Ai o listă de zece milioane de tranzacții, iar fiecare are doar un customer ID. Ai nevoie de numele reale ale clienților atașate acelor tranzacții. Dacă scrii un loop în Python sau folosești un dictionary mapping ca să potrivești acele ID-uri cu nume, irosești cicluri de CPU și memorie. Pandas are un engine optimizat, construit special pentru operațiuni în stil SQL, într-o singură linie de cod. Astăzi vorbim despre algebra relațională: merge și join. Înainte să mergem mai departe, hai să clarificăm o confuzie frecventă. Lumea confundă adesea un merge cu o concatenare. Concatenarea înseamnă doar să pui fizic array-uri unul peste altul sau unul lângă altul. Merge-ul este complet diferit. Merge-ul este pentru join-uri de baze de date relaționale. Aliniază rândurile din două tabele diferite pe baza valorilor unor chei comune. Funcția de bază pentru asta este pandas dot merge. Ia două DataFrame-uri, pe care le numim left table și right table. Gândește-te înapoi la scenariul nostru cu tranzacții. DataFrame-ul tău din stânga este un fact table masiv care conține milioane de achiziții. DataFrame-ul tău din dreapta este un dimension table mai mic, care conține detalii despre clienți, cum ar fi nume și adrese de email. Ambele tabele au în comun o coloană numită customer ID. Acest setup specific se numește un many-to-one join. Ai multe tranzacții care aparțin unui singur client. Când le dai merge folosind cheia customer ID, pandas ia înregistrarea unică a clientului din tabelul din dreapta și îi dă broadcast peste toate tranzacțiile care se potrivesc din tabelul din stânga. Aici e ideea de bază. Cel mai critic parametru pe care îl controlezi este argumentul how. Acesta dictează ce chei supraviețuiesc merge-ului și ajung în rezultatul final. By default, pandas folosește un inner join. Dacă nu specifici argumentul how, rezultatul păstrează doar rândurile în care acel customer ID există în ambele tabele. Dacă un client a făcut o tranzacție, dar înregistrarea lui a fost ștearsă din baza de date cu clienți, acea tranzacție dispare complet din rezultatul tău după merge. Ca să previi pierderea datelor din tabelul tău principal, folosești un left join. Dacă pasezi left argumentului how, pandas păstrează absolut fiecare rând din tabelul tău din stânga, care este lista ta masivă de tranzacții. Dacă o tranzacție are un customer ID care nu există în tabelul din dreapta, pandas păstrează totuși rândul tranzacției, dar umple detaliile lipsă ale clientului cu valori Not a Number. Asta este exact logica pe care o vrei atunci când atașezi detalii din dimension table la un fact table principal. Exact opusul este un right join. Dacă pasezi right, păstrezi toate rândurile din dimension table-ul clienților, indiferent dacă au sau nu tranzacții care se potrivesc în tabelul din stânga. Te alegi cu o listă cu toți clienții, iar cei care nu au cumpărat nimic vor avea pur și simplu missing values pentru datele tranzacției. În cele din urmă, există outer join. Pasează outer argumentului how, iar pandas păstrează totul. Face uniunea cheilor din ambele frame-uri. Fiecare tranzacție și fiecare client ajunge în dataset-ul final, cu missing values care umplu golurile oriunde nu se găsește un match perfect. Inner join-ul default elimină silențios datele care nu se potrivesc, așa că, dacă nu vrei în mod explicit să filtrezi rânduri, ar trebui să specifici mereu un left join atunci când atașezi lookup tables la dataset-ul tău principal. Asta e tot pentru acest episod. Mulțumesc că m-ai ascultat și continuă să construiești!
6

Șablonul Split-Apply-Combine

3m 45s

Deblochează adevărata putere a obiectului GroupBy. Vei învăța cum să treci dincolo de mediile simple pentru a efectua transformări și filtrări complexe specifice grupurilor.

Descarcă
Salut, sunt Alex de la DEV STORIES DOT EU. Mastering Modern Pandas, episodul 6 din 8. Probabil crezi că gruparea datelor înseamnă doar să aduni numere pentru a găsi un total sau o medie. Dar ce faci dacă trebuie să evaluezi un singur row pe baza comportamentului grupului din care face parte, fără să pierzi forma originală a dataset-ului tău? Asta necesită să treci dincolo de simple rezumate și să folosești pattern-ul Split-Apply-Combine. Când apelezi o metodă groupby în pandas, declanșezi un proces secvențial în trei pași. Primul este pasul de split. Pandas ia întregul tău dataset și îl împarte în grupuri independente pe baza unei chei pe care o furnizezi. Urmează pasul de apply, unde o funcție este executată pe fiecare grup, complet independent de celelalte. În cele din urmă, pasul de combine ia rezultatele din fiecare grup și le îmbină la loc într-o singură structură de date. Mulți developeri cred că pasul de apply este strict pentru agregare. Agregarea ia un grup de valori și returnează un singur număr, cum ar fi suma sau media. Dacă grupezi un dataset de customer support după agent și ceri timpul mediu de rezolvare, obții un nou dataset cu un row per agent. Asta este util, dar reprezintă doar o treime din poveste. Iată ideea cheie. Pasul de apply este la fel de frecvent folosit pentru transformare și filtrare. O transformare face un calcul pe grup, dar returnează un obiect care este indexat exact ca datele originale. Nu reduce numărul de rows. Să ne întoarcem la dataset-ul nostru de customer support. Vrei să știi dacă un anumit tichet a durat neobișnuit de mult ca să fie rezolvat. Dar un timp neobișnuit pentru un agent junior ar putea fi un timp normal pentru un agent senior care gestionează probleme foarte complexe. Ai nevoie de z-score-ul timpului de rezolvare, relativ doar la media istorică a acelui agent specific. Faci split la date după agent și aplici o funcție de transformare care calculează z-score-ul. Pandas calculează media și deviația standard pentru agentul A, standardizează tichetele agentului A, face exact același lucru pentru agentul B, și apoi le combină. Primești înapoi dataset-ul original, row cu row, dar acum fiecare tichet are un scor standardizat bazat strict pe contextul specific al grupului său. A treia aplicație principală este filtrarea. Asta îți permite să elimini grupuri întregi pe baza unei proprietăți colective, în loc să evaluezi rows individuale. Să presupunem că vrei să analizezi acele z-scores ale tichetelor, dar unii agenți din dataset-ul tău au procesat doar două sau trei tichete. Mediile lor sunt irelevante statistic. Poți folosi o funcție de filtrare pe obiectul grupat pentru a verifica dimensiunea fiecărui grup. Dacă un grup are mai puțin de zece tichete, logica de filtrare returnează false, iar pandas face drop la fiecare row care aparține acelui agent. Pasul de combine returnează apoi un dataset care conține doar tichetele de la agenții cu o dimensiune validă a eșantionului. Faci split la date după o cheie, aplici o regulă logică care evaluează grupul și dai combine la supraviețuitori. Agregarea reduce datele. Transformarea standardizează datele în contextul lor local. Filtrarea elimină datele pe baza regulilor de grup. Adevărata putere a pattern-ului split-apply-combine este că îți permite să manipulezi rows individuale folosind contextul la nivel de grup, fără să scrii vreodată un loop manual. Dacă aceste deep dives ți se par utile și vrei să susții emisiunea, poți căuta DevStoriesEU pe Patreon. Aș vrea să îmi iau un moment să îți mulțumesc că ne asculți — ne ajută foarte mult. Să ai o zi super!
7

Stăpânirea seriilor de timp

4m 34s

Ne scufundăm în dominația incontestabilă a pandas în analiza seriilor de timp. Vei învăța cum să folosești DatetimeIndex și funcția nativă de resampling pentru date de înaltă frecvență.

Descarcă
Salut, sunt Alex de la DEV STORIES DOT EU. Mastering Modern Pandas, episodul 7 din 8. Să implementezi manual propriile agregări de timp este un coșmar cu intervale lipsă, ani bisecți și logică de business days. Dacă te trezești că scrii custom code pentru a rotunji raw timestamps în buckets regulate, muncești mult prea mult. Soluția este Time Series Mastery folosind structurile temporale native din pandas. Coloana vertebrală a funcționalității de time series în pandas este DatetimeIndex. În loc de numere întregi standard pentru rânduri, indexul de dataframe devine o secvență strictă de timestamps precise. Trecerea indexului la un DatetimeIndex schimbă fundamental modul în care se comportă acel dataframe, făcând întreaga structură temporally aware. Acest lucru permite slicing nativ bazat pe timp. Dacă ai nevoie de date doar din octombrie 2023, pasezi un simplu string „2023-10” către row locator. Pandas calculează automat limitele exacte la nivel de microsecundă pentru luna respectivă și returnează subsetul corect. Poți pasa string-uri de date parțiale până la nivel de oră sau minut, iar indexul rezolvă matematica de timestamp din spate. Odată ce datele tale sunt temporally aware, de obicei trebuie să le agreghezi. Mulți developeri confundă resampling-ul bazat pe timp cu un grouping de bază. Ei încearcă să aplice operațiuni standard de group-by pe o coloană de date. Această abordare eșuează atunci când lucrezi cu time series dezordonate din lumea reală. Un grouping standard se uită doar la rândurile explicite prezente în acel moment în dataframe-ul tău. Dacă un server este offline timp de o oră, o operațiune standard de group-by pur și simplu sare complet peste acea oră. Timeline-ul tău de output va avea un gol ascuns, dând peste cap orice calcule ulterioare bazate pe timp. Iată ideea cheie. Metoda dot resample este fundamental diferită, deoarece înțelege nativ logica de calendar. Ea proiectează un time grid rigid și continuu peste datele tale. Dacă faci resample la intervale de zece minute, și nu sosesc date într-o anumită fereastră de zece minute, pandas tot generează acel bucket. Lasă valorile goale, păstrând integritatea matematică strictă a timeline-ului tău. Resampling-ul înțelege în mod inerent intervalele goale, lungimile neregulate ale lunilor și calendarele de business days care exclud weekendurile și sărbătorile legale. Ia în considerare scenariul unui analist cantitativ care procesează date de trading. Primești tick data de înaltă frecvență de la un exchange. Tranzacțiile individuale sosesc la intervale complet neregulate, uneori trei pe microsecundă, alteori niciuna timp de douăzeci de secunde. Modelul tău de pricing nu poate consuma acest haos. Are nevoie de bare de cinci minute perfect aliniate. Deoarece prețurile tranzacțiilor tale sunt mapate la un DatetimeIndex, apelezi metoda dot resample pe dataframe-ul tău și pasezi string-ul de frecvență „5min”. Asta mapează fiecare tick neregulat la un grid strict de cinci minute. Pentru a alimenta un model financiar, ai nevoie în mod specific de prețurile Open, High, Low și Close pentru fiecare bucket. În loc să scrii funcții custom pentru a extrage prima, maxima, minima și ultima tranzacție din fiecare fereastră, faci chain la metoda dot ohlc direct pe apelul tău de resample. Pandas calculează toate cele patru metrici simultan, generând un dataset structurat curat de bare de cinci minute. Acele intervale goale menționate anterior rămân intacte în acest output. Apoi poți face chain la o altă metodă pentru a da forward-fill prețurilor de închidere anterioare în golurile goale, asigurându-te că modelul tău are întotdeauna date valide. Resampling-ul transformă înregistrările neregulate, event-driven, într-un timeline previzibil și solid din punct de vedere matematic, fără să îți ceară să scrii o singură linie de logică de calendar. Mersi că ne-ai ascultat. Pe data viitoare!
8

Scalarea la seturi de date Out-of-Core

4m 29s

Abordăm limitele memoriei RAM a mașinii tale. Vei învăța cum să procesezi seturi de date semnificativ mai mari decât memoria folosind exclusiv chunking în pandas.

Descarcă
Salut, sunt Alex de la DEV STORIES DOT EU. Mastering Modern Pandas, episodul 8 din 8. Înainte să ceri o instanță masivă de cloud sau să apelezi la un cluster de calcul distribuit, s-ar putea să fii surprins să afli că poți procesa terabytes de date direct pe laptop. Majoritatea erorilor out-of-memory nu necesită un framework nou, ci doar o schimbare în modul în care citești fișierele. Astăzi, discutăm despre scalarea la dataseturi out-of-core. Procesarea out-of-core înseamnă pur și simplu să lucrezi cu dataseturi mai mari decât memoria RAM disponibilă a sistemului tău. O reacție comună la un crash out-of-memory este să presupui că pandas și-a atins limita absolută. Lumea sare adesea direct la rescrierea pipeline-urilor în PySpark sau Dask. Dar pandas poate gestiona nativ date masive dacă nu mai încerci să încarci tot datasetul în RAM dintr-o dată. Pattern-urile simple cu generatori rezolvă marea majoritate a acestor probleme de scalare. Mecanismul principal pentru procesarea out-of-core este chunking-ul. Dacă ai de-a face cu un singur fișier text masiv, funcția standard read acceptă un argument chunk size. Când pasezi acest argument, pandas nu mai returnează un DataFrame. În schimb, returnează un iterator. De fiecare dată când codul tău avansează iteratorul, pandas citește de pe disc doar numărul specificat de rânduri și le dă yield sub forma unui DataFrame normal. Aplici logica ta pe acel chunk, extragi rezultatul și apoi arunci chunk-ul. Pentru că datele vechi sunt șterse din memorie înainte să fie citit următorul batch, consumul tău de memorie rămâne complet constant, indiferent de cât de mare este fișierul în sine. Aici devine interesant. Infrastructura modernă de date se bazează rareori pe un singur fișier text gigantic. De obicei, dataseturile mari sunt stocate ca directoare care conțin sute de fișiere mai mici, partiționate, de regulă într-un format binar precum Parquet. Fișierele Parquet sunt foarte comprimate și se încarcă extrem de rapid, dar tot nu poți încărca cincizeci de gigabytes de fișiere Parquet în șaisprezece gigabytes de RAM. Pentru a gestiona asta, aplici manual conceptul de chunking pe toate fișierele. Imaginează-ți că ai un director cu fișiere Parquet anuale și vrei să calculezi frecvența totală a categoriilor pe întregul dataset istoric. Construiești un loop iterativ simplu. Mai întâi, inițializezi un pandas Series gol. Acesta va acționa ca acumulator pentru totalurile globale. Apoi, iterezi prin director, fișier cu fișier. În interiorul loop-ului, citești fișierul curent într-un DataFrame. Acum, rulezi funcția value counts pe coloana specifică pe care o analizezi. Asta îți oferă un Series care conține frecvențele doar pentru acel an specific. Pasul crucial este combinarea acestui rezultat local cu acumulatorul tău global. Faci asta apelând metoda add pe Series-ul tău global și pasând Series-ul local. Pentru că unele categorii ar putea exista într-un fișier, dar nu și în altul, trebuie să setezi argumentul fill value la zero. Asta te asigură că pandas aliniază corect indecșii și adună valorile fără să introducă missing values. Odată ce loop-ul termină de procesat acel fișier, trece la următorul. Python face automat garbage collect la vechiul DataFrame. Practic, faci streaming la un dataset masiv prin memorie, fișier cu fișier, construind o agregare globală continuă. Procesarea out-of-core nu înseamnă să arunci cu hardware într-o problemă. Este vorba despre a-ți menține starea activă mică și a împinge agregările matematice la nivelul fiecărui chunk individual. Fiindcă acesta este sfârșitul seriei, te încurajez insistent să explorezi documentația oficială pandas despre scalare și să încerci aceste pattern-uri hands-on cu propriile tale date. Dacă ai subiecte pe care vrei să le abordăm în seriile viitoare, vizitează devstories dot eu și dă-ne de veste. Îți mulțumesc că ai petrecut câteva minute cu mine. Până data viitoare, numai bine.