$$ \newcommand{\floor}[1]{\left\lfloor{#1}\right\rfloor} \newcommand{\ceil}[1]{\left\lceil{#1}\right\rceil} \renewcommand{\mod}{\,\mathrm{mod}\,} \renewcommand{\div}{\,\mathrm{div}\,} \newcommand{\metar}{\,\mathrm{m}} \newcommand{\cm}{\,\mathrm{cm}} \newcommand{\dm}{\,\mathrm{dm}} \newcommand{\litar}{\,\mathrm{l}} \newcommand{\km}{\,\mathrm{km}} \newcommand{\s}{\,\mathrm{s}} \newcommand{\h}{\,\mathrm{h}} \newcommand{\minut}{\,\mathrm{min}} \newcommand{\kmh}{\,\mathrm{\frac{km}{h}}} \newcommand{\ms}{\,\mathrm{\frac{m}{s}}} \newcommand{\mss}{\,\mathrm{\frac{m}{s^2}}} \newcommand{\mmin}{\,\mathrm{\frac{m}{min}}} \newcommand{\smin}{\,\mathrm{\frac{s}{min}}} $$

Prijavi problem


Obeleži sve kategorije koje odgovaraju problemu

Još detalja - opišite nam problem


Uspešno ste prijavili problem!
Status problema i sve dodatne informacije možete pratiti klikom na link.
Nažalost nismo trenutno u mogućnosti da obradimo vaš zahtev.
Molimo vas da pokušate kasnije.

Средњошколци у Републици Србији

У овом темату позабавићемо се подацима о средњошколском образовању у Републици Србији који су нам доступни кроз отворене податке Министарства за просвету, науку и технолошки развој: http://opendata.mpn.gov.rs. Фајлови о средњошколцима и средњим школама у .csv формату (преузети 01.12.2019.) налазе се у локалном фолдеру и у редовима који следе, бавићемо се кратком прерадом тих података за лакшу обраду у наредним радним свескама. Специјално, користећи библиотеку pandas за учитавање и анализу табеларних података ћемо:

  • брисати непотребне колоне
  • додавати нове колоне на основу рачунских операцијама над постојећим подадацма
  • уз помоћ библиотеке cyrtranslit ћемо мењати текстуалне вредности из латиничног у ћирилично писмо и обратно
  • груписати податке и спајати их у нове табеле
  • сачувати припремљен фајл за даљу обраду
In [1]:
import pandas as pd
import numpy as np
import cyrtranslit

Учитавање и обрада табеларних података је изузетно једноставна и практична у библиотеци pandas због чега је она изузетно популарна. Податке о средњошколцима и средњим школама преузели смо у .csv формату (вредности раздвојене зарезом, енг. coma separated values), па ћемо их учитати функцијом read_csv:

In [3]:
data = pd.read_csv('data/srednjoskolci data/raw data/MPNTRopendata_ss.csv')

У учитане податке брзо можемо завирити на пар следећих начина:

Функција head() излистава првих 5 редова табеле, док head(n) излистава n првих редова:

In [3]:
data.head(1)
Out[3]:
# ИД установе Власништво Округ Општина Назив установе Подручје рада Образовни профил Трајање образовања Језик наставе ... Број ИОП-а 2 - трећи разред Број ИОП-а 3 - трећи разред Број одељења - четврти разред Број комбинованих одељења - четврти разред Број специјалних одељења - четврти разред Број ученика - четврти разред Број девојчица - четврти разред Број ИОП-а 1 - четврти разред Број ИОП-а 2 - четврти разред Број ИОП-а 3 - четврти разред
0 1.0 1322 Државно Севернобачки управни округ Бачка Топола Пољопривредна школа Пољопривреда, производња и прерада хране Пољопривредни техничар 4 Мађарски језик ... 0 0 1 0 0 18 6 0 0 0

1 rows × 42 columns

Како учитана табела има чак 42 колоне, не можемо их видети све. Међутим, функцијом info() можемо сазнати које све колоне табела има, колико има уноса, као и које типове података је препознао пајтон у учитавању:

In [4]:
data.info()
<class 'pandas.core.frame.DataFrame'>
RangeIndex: 3180 entries, 0 to 3179
Data columns (total 42 columns):
#                                             3180 non-null float64
ИД установе                                   3180 non-null int64
Власништво                                    3180 non-null object
Округ                                         3180 non-null object
Општина                                       3180 non-null object
Назив установе                                3180 non-null object
Подручје рада                                 3180 non-null object
Образовни профил                              3180 non-null object
Трајање образовања                            3180 non-null int64
Језик наставе                                 3180 non-null object
Број одељења - први разред                    3180 non-null int64
Број комбинованих одељења - први разред       3180 non-null int64
Број специјалних одељења - први разред        3180 non-null int64
Број ученика - први разред                    3180 non-null int64
Број девојчица - први разред                  3180 non-null int64
Број ИОП-а 1 - први разред                    3180 non-null int64
Број ИОП-а 2 - први разред                    3180 non-null int64
Број ИОП-а 3 - први разред                    3180 non-null int64
Број одељења - други разред                   3180 non-null int64
Број комбинованих одељења - други разред      3180 non-null int64
Број специјалних одељења - други разред       3180 non-null int64
Број ученика - други разред                   3180 non-null int64
Број девојчица - други разред                 3180 non-null int64
Број ИОП-а 1 - други разред                   3180 non-null int64
Број ИОП-а 2 - други разред                   3180 non-null int64
Број ИОП-а 3 - други разред                   3180 non-null int64
Број одељења - трећи разред                   3180 non-null int64
Број комбинованих одељења - трећи разред      3180 non-null int64
Број специјалних одељења - трећи разред       3180 non-null int64
Број ученика - трећи разред                   3180 non-null int64
Број девојчица - трећи разред                 3180 non-null int64
Број ИОП-а 1 - трећи разред                   3180 non-null int64
Број ИОП-а 2 - трећи разред                   3180 non-null int64
Број ИОП-а 3 - трећи разред                   3180 non-null int64
Број одељења - четврти разред                 3180 non-null int64
Број комбинованих одељења - четврти разред    3180 non-null int64
Број специјалних одељења - четврти разред     3180 non-null int64
Број ученика - четврти разред                 3180 non-null int64
Број девојчица - четврти разред               3180 non-null int64
Број ИОП-а 1 - четврти разред                 3180 non-null int64
Број ИОП-а 2 - четврти разред                 3180 non-null int64
Број ИОП-а 3 - четврти разред                 3180 non-null int64
dtypes: float64(1), int64(34), object(7)
memory usage: 1.0+ MB

Овај сет података садржи информације о срењим школама и образовним профилима у њима. Поред географских одредница школе (општина, округ), за сваки образовни профил имамо информације о броју ученика по разредима, броју одељења и слично што можете видети из назива колона. Овај интересантан сет података у наредним радним свескама користићемо да сазнамо који су то популарни смерови, да ли се то разликује по окрузима и слично.

Функцијом describe() још детаљније можемо завирити у колоне које садрже нумеричке податке. Она нам даје преглед основне статистике - број уноса, просечну вредност (mean), стандардну девијацију (std), најмању (min), највећу (max), медијалну вредност (50%), кaо и вредности које су веће од 25% других и 75% других у одређеној нумеричкој колони.

In [5]:
data.describe()
Out[5]:
# ИД установе Трајање образовања Број одељења - први разред Број комбинованих одељења - први разред Број специјалних одељења - први разред Број ученика - први разред Број девојчица - први разред Број ИОП-а 1 - први разред Број ИОП-а 2 - први разред ... Број ИОП-а 2 - трећи разред Број ИОП-а 3 - трећи разред Број одељења - четврти разред Број комбинованих одељења - четврти разред Број специјалних одељења - четврти разред Број ученика - четврти разред Број девојчица - четврти разред Број ИОП-а 1 - четврти разред Број ИОП-а 2 - четврти разред Број ИОП-а 3 - четврти разред
count 3180.000000 3180.000000 3180.000000 3180.000000 3180.000000 3180.000000 3180.000000 3180.000000 3180.000000 3180.000000 ... 3180.000000 3180.000000 3180.000000 3180.000000 3180.000000 3180.000000 3180.000000 3180.000000 3180.000000 3180.000000
mean 1590.500000 1555.244340 3.687421 0.877044 0.142453 0.009434 21.407233 10.210377 0.033333 0.175157 ... 0.068553 0.011321 0.681132 0.011635 0.000943 16.887736 8.858491 0.029245 0.016667 0.008805
std 918.131254 149.038699 0.482893 0.858854 0.362816 0.108924 25.280818 16.482580 0.221853 0.581631 ... 0.330411 0.402724 0.926467 0.126124 0.039648 25.981561 16.208440 0.227325 0.158751 0.315158
min 1.000000 1322.000000 1.000000 0.000000 0.000000 0.000000 0.000000 0.000000 0.000000 0.000000 ... 0.000000 0.000000 0.000000 0.000000 0.000000 0.000000 0.000000 0.000000 0.000000 0.000000
25% 795.750000 1424.000000 3.000000 0.000000 0.000000 0.000000 0.000000 0.000000 0.000000 0.000000 ... 0.000000 0.000000 0.000000 0.000000 0.000000 0.000000 0.000000 0.000000 0.000000 0.000000
50% 1590.500000 1557.000000 4.000000 1.000000 0.000000 0.000000 19.000000 4.000000 0.000000 0.000000 ... 0.000000 0.000000 1.000000 0.000000 0.000000 5.000000 0.000000 0.000000 0.000000 0.000000
75% 2385.250000 1661.250000 4.000000 1.000000 0.000000 0.000000 30.000000 15.000000 0.000000 0.000000 ... 0.000000 0.000000 1.000000 0.000000 0.000000 27.000000 14.000000 0.000000 0.000000 0.000000
max 3180.000000 1976.000000 4.000000 9.000000 4.000000 3.000000 287.000000 197.000000 3.000000 9.000000 ... 5.000000 22.000000 9.000000 4.000000 2.000000 268.000000 154.000000 4.000000 3.000000 17.000000

8 rows × 35 columns

Како је табела написана ћирилицом, користићемо библиотеку cyrtranslit да све текстуалне податке у табели преиначимо у латиничо писмо (то нам је посебно битно за називе колона како бисмо лакше баратали подацима). За почетак ћемо то урадити са називима колона које добијамо позивајући data.columns.

In [6]:
data.columns = [cyrtranslit.to_latin(text,'sr') for text in list(data.columns)]
data.head(1)
Out[6]:
# ID ustanove Vlasništvo Okrug Opština Naziv ustanove Područje rada Obrazovni profil Trajanje obrazovanja Jezik nastave ... Broj IOP-a 2 - treći razred Broj IOP-a 3 - treći razred Broj odeljenja - četvrti razred Broj kombinovanih odeljenja - četvrti razred Broj specijalnih odeljenja - četvrti razred Broj učenika - četvrti razred Broj devojčica - četvrti razred Broj IOP-a 1 - četvrti razred Broj IOP-a 2 - četvrti razred Broj IOP-a 3 - četvrti razred
0 1.0 1322 Државно Севернобачки управни округ Бачка Топола Пољопривредна школа Пољопривреда, производња и прерада хране Пољопривредни техничар 4 Мађарски језик ... 0 0 1 0 0 18 6 0 0 0

1 rows × 42 columns

А у наредних пар редова пролазимо кроз целокупан садржај појединачних колона које смо препознали да су текстуалне и да су нам од користи у наставку, а затим њихов садржај мењамо у латинично писмо. Урадићемо за почетак то за колону 'Власништво'.

In [7]:
data['Vlasništvo'] = [cyrtranslit.to_latin(text,'sr') for text in list(data['Vlasništvo'])]
data.head(1)
Out[7]:
# ID ustanove Vlasništvo Okrug Opština Naziv ustanove Područje rada Obrazovni profil Trajanje obrazovanja Jezik nastave ... Broj IOP-a 2 - treći razred Broj IOP-a 3 - treći razred Broj odeljenja - četvrti razred Broj kombinovanih odeljenja - četvrti razred Broj specijalnih odeljenja - četvrti razred Broj učenika - četvrti razred Broj devojčica - četvrti razred Broj IOP-a 1 - četvrti razred Broj IOP-a 2 - četvrti razred Broj IOP-a 3 - četvrti razred
0 1.0 1322 Državno Севернобачки управни округ Бачка Топола Пољопривредна школа Пољопривреда, производња и прерада хране Пољопривредни техничар 4 Мађарски језик ... 0 0 1 0 0 18 6 0 0 0

1 rows × 42 columns

Наредне колоне можемо обрадити тако што ћемо претходни ред написати више пута, за све различите колоне које желимо да преименујемо у латинично писмо, или тако што ћемо овај ред написати у одговарајућој петљи којом ћемо проћи кроз све колоне које желимо да обрадимо:

In [8]:
tekstualne_kolone = ['Vlasništvo', 'Okrug','Opština','Naziv ustanove', 'Područje rada', 'Obrazovni profil', 'Jezik nastave']

for kolona in tekstualne_kolone:
    data[kolona] = [cyrtranslit.to_latin(text,'sr') for text in list(data[kolona])]
data.head(1)
Out[8]:
# ID ustanove Vlasništvo Okrug Opština Naziv ustanove Područje rada Obrazovni profil Trajanje obrazovanja Jezik nastave ... Broj IOP-a 2 - treći razred Broj IOP-a 3 - treći razred Broj odeljenja - četvrti razred Broj kombinovanih odeljenja - četvrti razred Broj specijalnih odeljenja - četvrti razred Broj učenika - četvrti razred Broj devojčica - četvrti razred Broj IOP-a 1 - četvrti razred Broj IOP-a 2 - četvrti razred Broj IOP-a 3 - četvrti razred
0 1.0 1322 Državno Severnobački upravni okrug Bačka Topola Poljoprivredna škola Poljoprivreda, proizvodnja i prerada hrane Poljoprivredni tehničar 4 Mađarski jezik ... 0 0 1 0 0 18 6 0 0 0

1 rows × 42 columns

Колоне које нам нису неопходне за предстојећу анализу избацићемо из табеле користећи функцију drop на следећи начин:

In [9]:
data=data.drop(columns=['#','Broj IOP-a 1 - prvi razred', 'Broj IOP-a 2 - prvi razred',
       'Broj IOP-a 3 - prvi razred','Broj IOP-a 1 - drugi razred', 'Broj IOP-a 2 - drugi razred',
       'Broj IOP-a 3 - drugi razred','Broj IOP-a 1 - treći razred', 'Broj IOP-a 2 - treći razred',
       'Broj IOP-a 3 - treći razred','Broj IOP-a 1 - četvrti razred', 'Broj IOP-a 2 - četvrti razred',
       'Broj IOP-a 3 - četvrti razred','Broj kombinovanih odeljenja - prvi razred',
                          'Broj kombinovanih odeljenja - drugi razred', 
                          'Broj kombinovanih odeljenja - treći razred',
                         'Broj kombinovanih odeljenja - četvrti razred',
                         'Broj specijalnih odeljenja - prvi razred',
                         'Broj specijalnih odeljenja - drugi razred',
                         'Broj specijalnih odeljenja - treći razred',
                         'Broj specijalnih odeljenja - četvrti razred'])
data.head()
Out[9]:
ID ustanove Vlasništvo Okrug Opština Naziv ustanove Područje rada Obrazovni profil Trajanje obrazovanja Jezik nastave Broj odeljenja - prvi razred ... Broj devojčica - prvi razred Broj odeljenja - drugi razred Broj učenika - drugi razred Broj devojčica - drugi razred Broj odeljenja - treći razred Broj učenika - treći razred Broj devojčica - treći razred Broj odeljenja - četvrti razred Broj učenika - četvrti razred Broj devojčica - četvrti razred
0 1322 Državno Severnobački upravni okrug Bačka Topola Poljoprivredna škola Poljoprivreda, proizvodnja i prerada hrane Poljoprivredni tehničar 4 Mađarski jezik 1 ... 8 1 21 8 1 11 3 1 18 6
1 1322 Državno Severnobački upravni okrug Bačka Topola Poljoprivredna škola Poljoprivreda, proizvodnja i prerada hrane Veterinarski tehničar 4 Mađarski jezik 1 ... 7 1 21 12 1 27 13 1 17 11
2 1322 Državno Severnobački upravni okrug Bačka Topola Poljoprivredna škola Poljoprivreda, proizvodnja i prerada hrane Prehrambeni tehničar 4 Mađarski jezik 1 ... 9 1 13 11 1 17 13 1 16 13
3 1322 Državno Severnobački upravni okrug Bačka Topola Poljoprivredna škola Poljoprivreda, proizvodnja i prerada hrane Rukovalac - mehaničar poljoprivredne tehnike 3 Mađarski jezik 1 ... 0 1 14 0 1 17 0 0 0 0
4 1322 Državno Severnobački upravni okrug Bačka Topola Poljoprivredna škola Poljoprivreda, proizvodnja i prerada hrane Mesar 3 Mađarski jezik 0 ... 0 1 13 1 0 0 0 0 0 0

5 rows × 21 columns

Како имамо на располагању колону о власништву школе, можемо проверити уносе за које је у овој колони означено приватно власништво. То радимо уз помоћ селектовања одређеног дела табеле, односно оног дела табеле за који важи да је data.Vlasništvo=='Privatno':

In [10]:
data[data.Vlasništvo=='Privatno']
Out[10]:
ID ustanove Vlasništvo Okrug Opština Naziv ustanove Područje rada Obrazovni profil Trajanje obrazovanja Jezik nastave Broj odeljenja - prvi razred ... Broj devojčica - prvi razred Broj odeljenja - drugi razred Broj učenika - drugi razred Broj devojčica - drugi razred Broj odeljenja - treći razred Broj učenika - treći razred Broj devojčica - treći razred Broj odeljenja - četvrti razred Broj učenika - četvrti razred Broj devojčica - četvrti razred
3112 1898 Privatno Grad Beograd Beograd - Novi Beograd Srednjoškolski obrazovni centar "SMARTANAC" Zdravstvo i socijalna zaštita Medicinska sestra - tehničar 4 Srpski jezik 0 ... 0 0 0 0 1 2 2 1 5 3
3113 1898 Privatno Grad Beograd Beograd - Novi Beograd Srednjoškolski obrazovni centar "SMARTANAC" Ostala delatnost ličnih usluga Frizer 3 Srpski jezik 0 ... 0 0 0 0 1 1 1 0 0 0
3114 1898 Privatno Grad Beograd Beograd - Novi Beograd Srednjoškolski obrazovni centar "SMARTANAC" Zdravstvo i socijalna zaštita Fizioterapeutski tehničar - novi nastavni program 4 Srpski jezik 0 ... 0 0 0 0 1 3 1 0 0 0

3 rows × 21 columns

Како су у питању само три уноса, за једну исту приватну школу, то значи да немамо репрезентативне информације о школама у приватном власништву. Стога ћемо се у наставку фокусирати само на школе које су у државном власништву и избацићемо из табеле ова три реда а затим и колону власништво:

In [11]:
data = data[data.Vlasništvo!='Privatno']
data = data.drop(columns=['Vlasništvo'])
data.head(2)
Out[11]:
ID ustanove Okrug Opština Naziv ustanove Područje rada Obrazovni profil Trajanje obrazovanja Jezik nastave Broj odeljenja - prvi razred Broj učenika - prvi razred Broj devojčica - prvi razred Broj odeljenja - drugi razred Broj učenika - drugi razred Broj devojčica - drugi razred Broj odeljenja - treći razred Broj učenika - treći razred Broj devojčica - treći razred Broj odeljenja - četvrti razred Broj učenika - četvrti razred Broj devojčica - četvrti razred
0 1322 Severnobački upravni okrug Bačka Topola Poljoprivredna škola Poljoprivreda, proizvodnja i prerada hrane Poljoprivredni tehničar 4 Mađarski jezik 1 24 8 1 21 8 1 11 3 1 18 6
1 1322 Severnobački upravni okrug Bačka Topola Poljoprivredna škola Poljoprivreda, proizvodnja i prerada hrane Veterinarski tehničar 4 Mađarski jezik 1 18 7 1 21 12 1 27 13 1 17 11

Како имамо податке о броју одељења по разреду и слично број ученика о разреду, у наставку ћемо додати још пар колона у којима ће се налазити подаци о укупном броју ученика, одељења сумирајући одговарајуће постојеће колоне.

In [12]:
data['Ukupno odeljenja'] = data['Broj odeljenja - prvi razred']+data['Broj odeljenja - drugi razred']+data['Broj odeljenja - treći razred']+data['Broj odeljenja - četvrti razred']
In [13]:
data['Ukupno učenika'] = data['Broj učenika - prvi razred']+data['Broj učenika - drugi razred']+data['Broj učenika - treći razred']+data['Broj učenika - četvrti razred']

Из колона са укупним бројем ученика и одељења по образовним профилима и смеровима, можемо израчунати и просечан број ученика у одељењу на сваком од профила:

In [14]:
data['Prosečan broj učenika u odeljenju'] = data['Ukupno učenika']/data['Ukupno odeljenja']

Међу подацима које обрађујемо имамо информације и о полу ученика, те ћемо из укупног броја ученика и укупног броја девојчица срачунати и број дечака. Поред укупног броја ученика по полу, израчунажемо и њихове процентуалне заступљености. За процентуалну заступљеност искористили смо и функцију round како бисмо ограничили број децимала на 2.

In [15]:
data['Ukupno devojcica'] = data['Broj devojčica - prvi razred']+data['Broj devojčica - drugi razred']+data['Broj devojčica - treći razred']+data['Broj devojčica - četvrti razred']
data['Ukupno decaka'] = data['Ukupno učenika']-data['Ukupno devojcica']
data['Procenat devojcica'] = round(100*data['Ukupno devojcica']/data['Ukupno učenika'],2)
data['Procenat decaka'] = 100-data['Procenat devojcica']

За анализу коју имамо у плану, неће нам бити потребни подаци о ученицима по разреду, стога ћемо и те колоне избрисати. (Ако имате на уму и неку анализу за коју је потребно да сачувате податке по разредима, прекочите наредну команду!)

In [16]:
data = data.drop(columns=['Broj odeljenja - prvi razred',
       'Broj učenika - prvi razred', 'Broj devojčica - prvi razred',
       'Broj odeljenja - drugi razred', 'Broj učenika - drugi razred',
       'Broj devojčica - drugi razred', 'Broj odeljenja - treći razred',
       'Broj učenika - treći razred', 'Broj devojčica - treći razred',
       'Broj odeljenja - četvrti razred', 'Broj učenika - četvrti razred',
       'Broj devojčica - četvrti razred'])
data.head(1)
Out[16]:
ID ustanove Okrug Opština Naziv ustanove Područje rada Obrazovni profil Trajanje obrazovanja Jezik nastave Ukupno odeljenja Ukupno učenika Prosečan broj učenika u odeljenju Ukupno devojcica Ukupno decaka Procenat devojcica Procenat decaka
0 1322 Severnobački upravni okrug Bačka Topola Poljoprivredna škola Poljoprivreda, proizvodnja i prerada hrane Poljoprivredni tehničar 4 Mađarski jezik 4 74 18.5 25 49 33.78 66.22

Ову нову табелу можемо сачувати у .csv формату користећи функцију to_csv:

In [17]:
data.to_csv('MPNTRopendata_ss_pripremljeni.csv',index=False)

Искористили смо и аргумент index да проследимо информацију функцији да не желимо да сачувамо колону индекс обзиром да се у њој налазе само редни бројеви и не носе додатно интересантне податке о средњошколцима.

Табела са подацима о средњим школама

Поред информација о заступљености одређених средњошколских профила и њиховој заузетости која је описана у претходној табели, имамо на располагању и неке опште податке о средњим школама, учитаћемо и припремити и те податке:

In [18]:
srednjeskole = pd.read_csv('data/srednjoskolci data/raw data/MPNTRopendata_ss_opsti.csv')
srednjeskole.head(2)
Out[18]:
# ИД установе Школска управа Округ Општина Насеље Назив установе Адреса Поштански број Адреса електронске поште ... Број специјалних одељења Број ученика Број девојчица Број ученика - ИОП 1 Број ученика - ИОП 2 Број ученика - ИОП 3 Број наставника - без замена Укупна норма наставникаа - без замена Број запослених - без замена Укупна норма запослених- без замена
0 1.0 1322 Сомбор Севернобачки управни округ Бачка Топола Бачка Топола Пољопривредна школа Маршала Тита 167 24300 psdirektor@gmail.com ... 0 524 222 3 6 0 74 65.9749 109 103.4649
1 2.0 1323 Сомбор Севернобачки управни округ Бачка Топола Бачка Топола Средња техничка школа Шинковић Јожеф Tрг Зорана Ђинђића 10 24300 sinjo@stcable.net ... 0 318 61 0 4 0 46 32.8130 60 46.0330

2 rows × 29 columns

Да бисмо видели све доступне колоне, искористићемо функцију columns:

In [19]:
srednjeskole.columns
Out[19]:
Index(['#', 'ИД установе', 'Школска управа', 'Округ', 'Општина', 'Насеље',
       'Назив установе', 'Адреса', 'Поштански број',
       'Адреса електронске поште', 'Телефон', 'Сајт', 'Матични број', 'ПИБ',
       'Датум оснивања', 'Примарна делатност', 'Власништво', 'Број одељења',
       'Број комбинованих одељења', 'Број специјалних одељења', 'Број ученика',
       'Број девојчица', 'Број ученика - ИОП 1', 'Број ученика - ИОП 2',
       'Број ученика - ИОП 3', 'Број наставника - без замена',
       'Укупна норма наставникаа - без замена', 'Број запослених - без замена',
       'Укупна норма запослених- без замена'],
      dtype='object')

Као и претходно, обрисаћемо неке од колона за које нам се чини да их нећемо даље анализирати:

In [20]:
srednjeskole = srednjeskole.drop(columns=['#','Школска управа', 'Насеље','Адреса', 'Поштански број',
       'Адреса електронске поште', 'Телефон', 'Сајт', 'Матични број', 'ПИБ',
       'Датум оснивања', 'Примарна делатност', 'Број ученика - ИОП 1', 'Број ученика - ИОП 2',
       'Број ученика - ИОП 3'])
srednjeskole.head()
Out[20]:
ИД установе Округ Општина Назив установе Власништво Број одељења Број комбинованих одељења Број специјалних одељења Број ученика Број девојчица Број наставника - без замена Укупна норма наставникаа - без замена Број запослених - без замена Укупна норма запослених- без замена
0 1322 Севернобачки управни округ Бачка Топола Пољопривредна школа Државно 26 5 0 524 222 74 65.9749 109 103.4649
1 1323 Севернобачки управни округ Бачка Топола Средња техничка школа Шинковић Јожеф Државно 15 3 0 318 61 46 32.8130 60 46.0330
2 1324 Севернобачки управни округ Суботица - град Гимназија Светозар Марковић Државно 36 0 0 855 535 76 66.1000 96 87.3000
3 1325 Севернобачки управни округ Суботица - град Економска средња школа Боса Милићевић Државно 28 6 0 762 483 72 59.8600 87 75.5500
4 1326 Севернобачки управни округ Суботица - град Средња медицинска школа Државно 24 0 0 684 566 125 61.5051 140 78.0051

Промена писма у називима и садржају колона:

In [21]:
srednjeskole.columns=[cyrtranslit.to_latin(text,'sr') for text in list(srednjeskole.columns)]
srednjeskole['Okrug']=[cyrtranslit.to_latin(text,'sr') for text in list(srednjeskole['Okrug'])]
srednjeskole['Opština']=[cyrtranslit.to_latin(text,'sr') for text in list(srednjeskole['Opština'])]
srednjeskole['Naziv ustanove']=[cyrtranslit.to_latin(text,'sr') for text in list(srednjeskole['Naziv ustanove'])]
srednjeskole['Vlasništvo']=[cyrtranslit.to_latin(text,'sr') for text in list(srednjeskole['Vlasništvo'])]

И као што смо претходно закључили, како немамо довољно података о школама у приватном власништву фокусираћемо се само на школе које су у државном власништву:

In [22]:
srednjeskole = srednjeskole[srednjeskole['Vlasništvo']=='Državno']
srednjeskole = srednjeskole.drop(columns=['Vlasništvo'])
srednjeskole.head(2)
Out[22]:
ID ustanove Okrug Opština Naziv ustanove Broj odeljenja Broj kombinovanih odeljenja Broj specijalnih odeljenja Broj učenika Broj devojčica Broj nastavnika - bez zamena Ukupna norma nastavnikaa - bez zamena Broj zaposlenih - bez zamena Ukupna norma zaposlenih- bez zamena
0 1322 Severnobački upravni okrug Bačka Topola Poljoprivredna škola 26 5 0 524 222 74 65.9749 109 103.4649
1 1323 Severnobački upravni okrug Bačka Topola Srednja tehnička škola Šinković Jožef 15 3 0 318 61 46 32.8130 60 46.0330

И ову табелу ћемо сачувати у csv формату:

In [23]:
srednjeskole.to_csv('MPNTRopendata_sskole_pripremljeni.csv',index=False)

Припрема података за анализу и визуализацију по окрузима:

Претхнодна табела о средњим школама садржи информације о округу и општини на којој се школа налази што се може искористити да се подаци агрегирају на нивоу ових просторних јединица и на тај начин можемо припремити податке за даљу анализу. За груписање по округу, користићемо фукцију groupby. Ова функција креира подтабеле редова који имају исту вредност по колони коју користимо као аргумент функције (на пример, ако групишемо по Округу, ишод су подтабеле за сваки округ). Ако не желимо целе подтабеле, често сумирамо по одређеним колонама (на пример када желимо да знамо укупан број ђака у сваком округу) или бројимо колико има вредности (на пример када желимо да знамо број школа или образовних профила). Хајде да видимо како то ради:

In [24]:
skolepookruzima = srednjeskole.groupby(['Okrug'])[['Broj učenika','Broj devojčica','Broj odeljenja','Broj nastavnika - bez zamena','Ukupna norma nastavnikaa - bez zamena']].sum()
skolepookruzima.head(3)
Out[24]:
Broj učenika Broj devojčica Broj odeljenja Broj nastavnika - bez zamena Ukupna norma nastavnikaa - bez zamena
Okrug
Borski upravni okrug 3281 1542 140 432 290.9780
Braničevski upravni okrug 4953 2452 196 525 393.9538
Grad Beograd 57359 28604 2096 5236 4534.7198

Проверите да ли су бројеви које смо на овај начин добили тачни. (Сугестија: селектујте делове табеле, нпр. skolepookruzima[skolepookruzima['Okrug']=='Borski upravni okrug'] ће излистати све редове у којима је округ Борски, користећи функцију sum можете проверити горње вредности.)

Како је овој новој табели индекс колона округ по коме смо груписали претходну табелу, ресетоваћемо индекс (користећи функцију reset_index), тј. индекс ће постати број:

In [25]:
skolepookruzima = skolepookruzima.reset_index()
skolepookruzima.head(3)
Out[25]:
Okrug Broj učenika Broj devojčica Broj odeljenja Broj nastavnika - bez zamena Ukupna norma nastavnikaa - bez zamena
0 Borski upravni okrug 3281 1542 140 432 290.9780
1 Braničevski upravni okrug 4953 2452 196 525 393.9538
2 Grad Beograd 57359 28604 2096 5236 4534.7198

Слично користећи функцију groupby и size за величину сваке од група, можемо у новој табели сачивати вредности о броју средњих школа по округу:

In [26]:
brsskolapookrugu = srednjeskole.groupby(['Okrug']).size().reset_index(name='Broj skola')
brsskolapookrugu.head()
Out[26]:
Okrug Broj skola
0 Borski upravni okrug 10
1 Braničevski upravni okrug 10
2 Grad Beograd 72
3 Jablanički upravni okrug 17
4 Južnobanatski upravni okrug 17

Претходно креиране две табеле skolepookruzima и brsskolapookrugu имају заједничку колону округ, па њу можемо искористи да на основу ње спојимо податке у једну табелу. То радимо уз помоћ функције merge којој је поред две табеле које спајамо потребно проследити и аргумент on којим дефинишемо по којој колони спајамо табеле:

In [27]:
infopookruzima = pd.merge(skolepookruzima,brsskolapookrugu,on='Okrug')
infopookruzima.head()
Out[27]:
Okrug Broj učenika Broj devojčica Broj odeljenja Broj nastavnika - bez zamena Ukupna norma nastavnikaa - bez zamena Broj skola
0 Borski upravni okrug 3281 1542 140 432 290.9780 10
1 Braničevski upravni okrug 4953 2452 196 525 393.9538 10
2 Grad Beograd 57359 28604 2096 5236 4534.7198 72
3 Jablanički upravni okrug 7677 3749 311 994 667.1526 17
4 Južnobanatski upravni okrug 8848 4281 341 970 748.8520 17

Направићемо још једну табелу која ће по окрузима пребројати број различитих опција за средњошколско образовање. Ове различите опције - број различитих подручја рада и број различитих образовних профила добићемо функцијом nunique:

In [28]:
opcijepookruzima = data.groupby(['Okrug'])[['Područje rada','Obrazovni profil']].nunique()
opcijepookruzima = opcijepookruzima.reset_index()
opcijepookruzima.head(3)
Out[28]:
Okrug Područje rada Obrazovni profil
0 Borski upravni okrug 9 52
1 Braničevski upravni okrug 9 52
2 Grad Beograd 16 206

И ове податке ћемо спојити са претходном табелом у којој су до сада сачувани прикупљени подаци по окрузима:

In [29]:
infopookruzima = pd.merge(infopookruzima,opcijepookruzima,on='Okrug')
infopookruzima.head()
Out[29]:
Okrug Broj učenika Broj devojčica Broj odeljenja Broj nastavnika - bez zamena Ukupna norma nastavnikaa - bez zamena Broj skola Područje rada Obrazovni profil
0 Borski upravni okrug 3281 1542 140 432 290.9780 10 9 52
1 Braničevski upravni okrug 4953 2452 196 525 393.9538 10 9 52
2 Grad Beograd 57359 28604 2096 5236 4534.7198 72 16 206
3 Jablanički upravni okrug 7677 3749 311 994 667.1526 17 15 77
4 Južnobanatski upravni okrug 8848 4281 341 970 748.8520 17 12 76

Коначно, један тип средњих школа има често специјалан статус - гимназије - па ћемо прикупити и податке колико се ученика школује у гимназијама на територији различитих округа:

In [30]:
gimnazijalci = data[data['Područje rada']=='Gimnazija'].groupby('Okrug')['Ukupno učenika'].sum()
gimnazijalci = gimnazijalci.reset_index()
gimnazijalci = gimnazijalci.rename(columns={'Ukupno učenika':'Ukupno gimnazijalaca'})
gimnazijalci.head(2)
Out[30]:
Okrug Ukupno gimnazijalaca
0 Borski upravni okrug 770
1 Braničevski upravni okrug 1137

И њих ћемо додати у табелу infopookruzima:

In [31]:
infopookruzima = pd.merge(infopookruzima,gimnazijalci,on='Okrug')
infopookruzima.head()
Out[31]:
Okrug Broj učenika Broj devojčica Broj odeljenja Broj nastavnika - bez zamena Ukupna norma nastavnikaa - bez zamena Broj skola Područje rada Obrazovni profil Ukupno gimnazijalaca
0 Borski upravni okrug 3281 1542 140 432 290.9780 10 9 52 770
1 Braničevski upravni okrug 4953 2452 196 525 393.9538 10 9 52 1137
2 Grad Beograd 57359 28604 2096 5236 4534.7198 72 16 206 18862
3 Jablanički upravni okrug 7677 3749 311 994 667.1526 17 15 77 1389
4 Južnobanatski upravni okrug 8848 4281 341 970 748.8520 17 12 76 1828

Табелу infopookruzima која сада садржи прегршт агрегираних података на нивоу округа ћемо сачувати у .csv за даљу анализу:

In [32]:
infopookruzima.to_csv('MPNTR_podaci_po_okruzima.csv',encoding='UTF-16',index=False)

Припрема података за анализу и визуализацију по општинама:

Слично ћемо поновити и са општинама. Како постоје примери оштина истог назива (нпр. Палилула), груписање ћемо сада вршити по пару колона - округ и општина:

In [33]:
skolepoopstinama = srednjeskole.groupby(['Okrug','Opština'])[['Broj učenika','Broj devojčica','Broj odeljenja','Broj nastavnika - bez zamena','Ukupna norma nastavnikaa - bez zamena']].sum()
skolepoopstinama = skolepoopstinama.reset_index()
skolepoopstinama.head(3)
Out[33]:
Okrug Opština Broj učenika Broj devojčica Broj odeljenja Broj nastavnika - bez zamena Ukupna norma nastavnikaa - bez zamena
0 Borski upravni okrug Bor 1544 751 64 184 130.8821
1 Borski upravni okrug Kladovo 465 210 19 51 38.8610
2 Borski upravni okrug Majdanpek 380 165 18 69 38.2098
In [34]:
brsskolapoopstini = srednjeskole.groupby(['Okrug','Opština']).size()
brsskolapoopstini = brsskolapoopstini.reset_index()
brsskolapoopstini = brsskolapoopstini.rename(columns={0:'Broj skola'})
brsskolapoopstini.head()
Out[34]:
Okrug Opština Broj skola
0 Borski upravni okrug Bor 4
1 Borski upravni okrug Kladovo 1
2 Borski upravni okrug Majdanpek 2
3 Borski upravni okrug Negotin 3
4 Braničevski upravni okrug Kostolac 1
In [35]:
infopoopstinama = pd.merge(skolepoopstinama,brsskolapoopstini,on=['Okrug','Opština'])
infopoopstinama.head()
Out[35]:
Okrug Opština Broj učenika Broj devojčica Broj odeljenja Broj nastavnika - bez zamena Ukupna norma nastavnikaa - bez zamena Broj skola
0 Borski upravni okrug Bor 1544 751 64 184 130.8821 4
1 Borski upravni okrug Kladovo 465 210 19 51 38.8610 1
2 Borski upravni okrug Majdanpek 380 165 18 69 38.2098 2
3 Borski upravni okrug Negotin 892 416 39 128 83.0251 3
4 Braničevski upravni okrug Kostolac 763 137 32 78 65.5550 1
In [36]:
opcijepoopstinama = data.groupby(['Okrug','Opština'])[['Područje rada','Obrazovni profil']].nunique()
opcijepoopstinama = opcijepoopstinama.reset_index()
opcijepoopstinama.head(3)
Out[36]:
Okrug Opština Područje rada Obrazovni profil
0 Borski upravni okrug Bor 9 30
1 Borski upravni okrug Kladovo 5 15
2 Borski upravni okrug Majdanpek 4 9
In [37]:
infopoopstinama = pd.merge(infopoopstinama,opcijepoopstinama,on=['Okrug','Opština'])
infopoopstinama.head()
Out[37]:
Okrug Opština Broj učenika Broj devojčica Broj odeljenja Broj nastavnika - bez zamena Ukupna norma nastavnikaa - bez zamena Broj skola Područje rada Obrazovni profil
0 Borski upravni okrug Bor 1544 751 64 184 130.8821 4 9 30
1 Borski upravni okrug Kladovo 465 210 19 51 38.8610 1 5 15
2 Borski upravni okrug Majdanpek 380 165 18 69 38.2098 2 4 9
3 Borski upravni okrug Negotin 892 416 39 128 83.0251 3 5 20
4 Braničevski upravni okrug Kostolac 763 137 32 78 65.5550 1 3 13
In [38]:
gimnazijalci = data[data['Područje rada']=='Gimnazija'].groupby(['Okrug','Opština'])['Ukupno učenika'].sum()
gimnazijalci = gimnazijalci.reset_index()
gimnazijalci = gimnazijalci.rename(columns={'Ukupno učenika':'Ukupno gimnazijalaca'})
gimnazijalci.head(2)
Out[38]:
Okrug Opština Ukupno gimnazijalaca
0 Borski upravni okrug Bor 303
1 Borski upravni okrug Kladovo 93
In [39]:
infopoopstinama = pd.merge(infopoopstinama,gimnazijalci,on=['Okrug','Opština'])
infopoopstinama.head()
Out[39]:
Okrug Opština Broj učenika Broj devojčica Broj odeljenja Broj nastavnika - bez zamena Ukupna norma nastavnikaa - bez zamena Broj skola Područje rada Obrazovni profil Ukupno gimnazijalaca
0 Borski upravni okrug Bor 1544 751 64 184 130.8821 4 9 30 303
1 Borski upravni okrug Kladovo 465 210 19 51 38.8610 1 5 15 93
2 Borski upravni okrug Majdanpek 380 165 18 69 38.2098 2 4 9 82
3 Borski upravni okrug Negotin 892 416 39 128 83.0251 3 5 20 292
4 Braničevski upravni okrug Petrovac na Mlavi 468 266 19 44 35.0179 1 3 5 210
In [40]:
trogodisnjepoopstini = data[data['Trajanje obrazovanja']==3].groupby(['Okrug','Opština'])['Ukupno učenika'].sum()
trogodisnjepoopstini = trogodisnjepoopstini.reset_index()
trogodisnjepoopstini = trogodisnjepoopstini.rename(columns={'Ukupno učenika':'Ukupno u trogodisnjim ss'})
trogodisnjepoopstini.head()
Out[40]:
Okrug Opština Ukupno u trogodisnjim ss
0 Borski upravni okrug Bor 163
1 Borski upravni okrug Kladovo 70
2 Borski upravni okrug Majdanpek 53
3 Borski upravni okrug Negotin 140
4 Braničevski upravni okrug Kostolac 78
In [41]:
infopoopstinama = pd.merge(infopoopstinama,trogodisnjepoopstini,on=['Okrug','Opština'])
infopoopstinama.head(2)
Out[41]:
Okrug Opština Broj učenika Broj devojčica Broj odeljenja Broj nastavnika - bez zamena Ukupna norma nastavnikaa - bez zamena Broj skola Područje rada Obrazovni profil Ukupno gimnazijalaca Ukupno u trogodisnjim ss
0 Borski upravni okrug Bor 1544 751 64 184 130.8821 4 9 30 303 163
1 Borski upravni okrug Kladovo 465 210 19 51 38.8610 1 5 15 93 70
In [42]:
infopoopstinama.to_csv('MPNTR_podaci_po_opstinama.csv',encoding='UTF-16',index=False)

У овој радној свесци испробали смо различите функције у оквиру pandas библиотеке, неке једноставне (као read_csv, head, info, drop, rename) али и неке захтевније (нпр. groupby, merge) све са циљем припреме података за даљу анализу и визуализације. А сада, хајде да видимо детљније шта нам говоре ови подаци!

In [ ]:
 
© 2021 Petlja.org Creative Commons License