[1] "Tea is better than coffee"
[1] 1
Zpracovávání výzkumných dat pomocí jazyka R
[ ]$dplyrU každé hodiny budou nyní cvičení na doma navíc. Bude se jednat o směs již probrané látky a problémů na zapřemýšlení. Jsou nepovinné - budete k nim mít i řešení, ale klidně mi je můžete poslat pro kontrolu / zpětnou vazbu.
V horním menu stránek kurzu nyní naleznete odkaz na rezervační stránku konzultací. Pokud něco budete potřebovat probrat, ať již obsah kurzu či pomoc s R, můžete mi bud´ napsat a nebo si zde přímo rezervovat termín. Součástí jsou i všeobecné R konzultace, pokud víte, že by je vaši kolegové využili, klidně odkaz předejte.
Vytvořte vektor, který v sobě bude mít větu “Tea is better than coffee”. Pokuste se přijít na to, jakým způsobem byste mohli z tohoto vektoru vytvořit druhý vektor, co bude obsahovat hodnoty “Tea” “is” “better” “than” “coffee”.
Vytvoříme vektor o jedné hodnotě "Tea is better than coffee".
Rozdělíme ho tak, že každé slovo bude vlastní hodnota.
Zkontrolujeme, zda je výsledek vektor.
Jedná se o list; je potřeba ho změnit na vektor.
Zontrolujeme, zda se jedná o vektor s počtem hodnot > 1.
Vytvořte list, který bude obsahovat informace o vašem oblíbeném filmu; jeho název, kdo jej režiséroval, kdy byl vydán, alespoň tři jména herců a hereček, kteří v něm hráli, na jaké ceny byl nominován a jaké společnosti se angažovaly jako jeho producenti. Jakmile budete mít list vytvořený, připojte do seznamu herců/hereček Zaphoda Beeblebroxe.
Vytvoříme list podle zadání.
$jmeno
[1] "The Adventures of Priscilla, Queen of the Desert"
$rezie
[1] "Stephan Elliott"
$rok
[1] 1994
$obsazeni
[1] "Hugo Weaving" "Guy Pearce" "Terence Stamp"
$oceneni
[1] "Academy Awards" "BAFTA"
$producenti
[1] "Michael Hamlyn and Al Clark"
Připojíme hodnotu "Zaphod Beeblebrox".
$jmeno
[1] "The Adventures of Priscilla, Queen of the Desert"
$rezie
[1] "Stephan Elliott"
$rok
[1] 1994
$obsazeni
[1] "Hugo Weaving" "Guy Pearce" "Terence Stamp"
[4] "Zaphod Beeblebrox"
$oceneni
[1] "Academy Awards" "BAFTA"
$producenti
[1] "Michael Hamlyn and Al Clark"
To je ale nějak komplikované, nešlo by to vyřešit jednodušeji?
Zkusme si připojit hodnotu "Ford Prefect" způsobem, který vám byl doporučován v materiálech, co jste na webu našli.
$jmeno
[1] "The Adventures of Priscilla, Queen of the Desert"
$rezie
[1] "Stephan Elliott"
$rok
[1] 1994
$obsazeni
[1] "Hugo Weaving" "Guy Pearce" "Terence Stamp"
[4] "Zaphod Beeblebrox" "Ford Prefect"
$oceneni
[1] "Academy Awards" "BAFTA"
$producenti
[1] "Michael Hamlyn and Al Clark"
Připojení jde provést pomocí práce s výběrem hodnot - takzvanou indexací. A přesně na to se tuto hodinu podíváme :).
Kolik odlišných hodnot je v následujícím vektoru?
[1] 3 2 7 45 2 6 11 7 90 76 4 3 46 45 7 89 6 45 1 55 12 90 2 67 2
[26] 8 7 4 34 6
Vytvořme si vektor obsahující hodnoty, které chceme analyzovat.
Ke zjištění, kolik odlišných/unikátních hodnot je v daném vektoru, můžeme dojít několika cestami. Jako první si ukážeme využití faktorizace.
Factor w/ 17 levels "1","2","3","4",..: 3 2 6 11 2 5 8 6 17 15 ...
[1] "1" "2" "3" "4" "6" "7" "8" "11" "12" "34" "45" "46" "55" "67" "76"
[16] "89" "90"
[1] 17
[1] 17
Můžeme k tomu ale použít i specifickou funkci unique.
Výběr specifických dat je jedna ze základních funkcí R; není pro to nutně třeba potřeba používat balíčky. Balíčky nám celý proces ovšem značně usnadní.
objekt ve kterém se vyhledává[pozice či charakteristiky vyhledávané hodnoty ve všech dimenzích]
objekt o jedné dimenzi: objekt[informace pro výběr hodnoty]
objekt o dvou dimenzích: objekt[řádek, sloupec]
objekt o třech dimenzích: objekt[řádek, sloupec, matice]
…
Jak víme, vektory mají pouze jednu dimenzi. Proto k definování pozice hodnot(y) stačí pouze jeden údaj.
a b c
558 67846 8797
c
8797
c
8797
Proč se u jména hodnoty používají uvozovky?
Je možné vybírat i více hodnot najednou. Jakým způsobem byste vybrali první a třetí hodnotu z objektu vektor?
Pro výběr více hodnot nepoužíváme čárku!
Na základě tohoto principu lze hodnoty vybírat pomocí různých způsobů:
Nyní dokážeme vybrat hodnoty podle čísla jejich pozice. Co když chceme ale vybrat hodnoty podle jejich charakteristik?
vektor[vektor < 600] = vyber z objektu vektor ty hodnoty, které splňují podmínku, že jsou menší než 600
a b c
TRUE FALSE FALSE
Proč nemůžeme jednoduše napsat vektor[< 600]?
Při < 600 chybí levá strana; co je menší než 600?
K výběru lze samozřejmě použít i ostatní operátory.
Vybírání specifických hodnot nemusíme ale používat pouze k jejich vyhledávání. Můžeme pomocí tohoto principu i přiřazovat a přepisovat jednotlivé hodnoty.
[1] 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
[1] 20
Pokud chceme, aby 2. hodnota x1 byla 55, jak ji můžeme přidat?
Co když ale chceme, aby číslo 55 bylo na pozici 42?
Vyber z následujícího vektoru poslední čtyři hodnoty
Vyber všechny hodnoty z vektoru krom té se jménem ageGroup. Nevypisuj ručně nový vektor, použij k výběru funkce či operátory.
Vyberte z čísel 1878 až 2324 pouze ty, které jsou dělitelné třemi. Kolik jich je?
Nápověda
Zapřemýšlejte se nad tím, co to znamená, že je číslo dělitelné třemi. Je možné si tuto charakteristiku ověřit nějakým operátorem?
Nezapomeňte, že indexace podle podmínek defacto není nic jiného než výběr hodnot pomocí TRUE a FALSE.
Vyber z čísel 1878 až 2324 pouze ty, které jsou dělitelné třemi. Kolik jich je?
Co znamená, že je číslo dělitelné třemi?
Po dělení třemi po něm nezůstane žádný zbytek. Jak toto v R zjistíme?
[1] 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0
[38] 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1
[75] 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2
[112] 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0
[149] 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1
[186] 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2
[223] 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0
[260] 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1
[297] 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2
[334] 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0
[371] 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1
[408] 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2 0 1 2
[445] 0 1 2
Chceme vybrat pouze ta čísla, která jsou dělitelná třemi -> nemají žádný zbytek -> zbytek je 0. Jak to provedeme?
[1] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[13] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[25] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[37] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[49] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[61] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[73] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[85] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[97] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[109] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[121] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[133] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[145] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[157] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[169] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[181] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[193] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[205] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[217] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[229] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[241] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[253] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[265] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[277] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[289] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[301] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[313] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[325] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[337] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[349] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[361] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[373] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[385] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[397] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[409] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[421] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[433] TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE
[445] TRUE FALSE FALSE
Máme v tuto chvíli sekvenci TRUE/FALSE hodnot, které popisují vlastnosti jednotivých hodnot ve vektoru cisla. Jak ji využijeme k indexaci?
[1] 1878 1881 1884 1887 1890 1893 1896 1899 1902 1905 1908 1911 1914 1917 1920
[16] 1923 1926 1929 1932 1935 1938 1941 1944 1947 1950 1953 1956 1959 1962 1965
[31] 1968 1971 1974 1977 1980 1983 1986 1989 1992 1995 1998 2001 2004 2007 2010
[46] 2013 2016 2019 2022 2025 2028 2031 2034 2037 2040 2043 2046 2049 2052 2055
[61] 2058 2061 2064 2067 2070 2073 2076 2079 2082 2085 2088 2091 2094 2097 2100
[76] 2103 2106 2109 2112 2115 2118 2121 2124 2127 2130 2133 2136 2139 2142 2145
[91] 2148 2151 2154 2157 2160 2163 2166 2169 2172 2175 2178 2181 2184 2187 2190
[106] 2193 2196 2199 2202 2205 2208 2211 2214 2217 2220 2223 2226 2229 2232 2235
[121] 2238 2241 2244 2247 2250 2253 2256 2259 2262 2265 2268 2271 2274 2277 2280
[136] 2283 2286 2289 2292 2295 2298 2301 2304 2307 2310 2313 2316 2319 2322
Vybrali jsme v tuto chvíli všechny čísla z 1878 až 2324, které jsou dělitelné třemi. Jak zjistíme, kolik jich je?
Matice narozdíl od vektoru mají již dvě dimenze; řádky a sloupce. Pro výběr nám tak už nestačí pouze jedno číslo.
Jak obě dimenze do výběru zapíšu? Vzpomeňte si na přehled ve Vyhledávání pomocí [ ]
[,1] [,2] [,3] [,4] [,5] [,6]
[1,] 10 14 18 22 26 30
[2,] 11 15 19 23 27 31
[3,] 12 16 20 24 28 32
[4,] 13 17 21 25 29 33
[1] 18
[1] 27
[1] 10 11 12 13
[1] 11 15 19 23 27 31
[,1] [,2]
[1,] 26 30
[2,] 27 31
[3,] 28 32
Můžeme k výběru používat i jména sloupců a řádků?
[1] 4 6
a b c d e f
A 10 14 18 22 26 30
B 11 15 19 23 27 31
C 12 16 20 24 28 32
D 13 17 21 25 29 33
[1] 18
[1] 19
a c d
A 10 18 22
B 11 19 23
C 12 20 24
D 13 21 25
Při výběru hodnot z matice používáme totožné principy jako při výběru z vektorů; jen se musí pro výběr definovat více dimenzí.1
Stejným způsobem, jako můžeme vybírat specifické hodnoty u vektoru, totéž můžeme provést i u matice.
a b c d e f
A 10 14 18 22 26 30
B 11 15 19 23 27 31
C 12 16 20 24 28 32
D 13 17 21 25 29 33
a b c d e f
C 12 16 20 24 28 32
D 13 17 21 25 29 33
Z kódu je zřejmé, že budeme vybírat všechny sloupce. Ale co znamená matice[,2] > 15 v řádcích?
A B C D
14 15 16 17
A B C D
FALSE FALSE TRUE TRUE
Pomocí tohoto kódu si vybereme pouze ty řádky, které splňují stanovenou podmínku.
a b c d e f
C 12 16 20 24 28 32
D 13 17 21 25 29 33
a b c d e f
C 12 16 20 24 28 32
D 13 17 21 25 29 33
Třeba jasně definovat podmínky pro všechny sloupce a řádky
Proč nemůžeme jednoduše použít následující kód?
Huh, proč se nám vybrala celá matice?
Jednotlivá písmena jsou v R uložena podle abecedy; B je tedy tak na druhé pozici.
Jak to že je ale 2 > 15?
2 > 1 = TRUEVznikne nám proto defakto následující pokyn:
a b c d e f
A 10 14 18 22 26 30
B 11 15 19 23 27 31
C 12 16 20 24 28 32
D 13 17 21 25 29 33
Pro to, aby výběr matice fungoval, tak je potřeba, aby se definovaly všechny řádky. Zde jsme ale dodali pouze jednu hodnotu. Víme ale, že R si v některých případech dokáže hodnoty samo doplnit, viz sekce Tvorba matice v druhé lekci.
Ve výsledku jsme R zadali následující kód:
Proč vám toto celé říkám?
Nemůžete počítat s tím, že když něco “pokazíte”, nutně vám vyskočí error.
R má spoustu funkcí a pokynů, i já někdy narazím na mně zcela nové věci
Kontrolujte si jednotlivé pokyny, které skládáte dohromady!
Vyber z prvního řádku matice ty sloupce, které mají hodnoty větší jak 25 nebo menší jak 15.
Vyber ty řádky matice, které mají ve sloupci c hodnotu přesně 20.
Zkušební datasety v R
V R je nainstalováno několik datasetů určených k zkoušení si funkcí a celkovému hraní si. Datasety HairEyeColor, který budeme v následujícím procvičení používat, je právě jeden z nich. Pro jeho používání není potřeba je jakkoliv nahrávat či ukládat jako proměnné. Stačí si pouze zavolat jeho jméno.
Kolik studentek, které se účastnily měření, má blond vlasy a zelené oči? Použijte dataset HairEyeColor.
Vybírání dimenzí
Pokud si nejste jisti jak postupovat, podívejte se znovu na poslední téma co jsme probírali a především na základ v Vyhledávání pomocí [ ] ;)
Kolik studentek, které se účastnily měření, má blond vlasy a zelené oči?
Nejdříve se podíváme na to, co je dataset HairEyeColor zač; jakou má strukturu? Jak vypadá?.
'table' num [1:4, 1:4, 1:2] 32 53 10 3 11 50 10 30 10 25 ...
- attr(*, "dimnames")=List of 3
..$ Hair: chr [1:4] "Black" "Brown" "Red" "Blond"
..$ Eye : chr [1:4] "Brown" "Blue" "Hazel" "Green"
..$ Sex : chr [1:2] "Male" "Female"
, , Sex = Male
Eye
Hair Brown Blue Hazel Green
Black 32 11 10 3
Brown 53 50 25 15
Red 10 10 7 7
Blond 3 30 5 8
, , Sex = Female
Eye
Hair Brown Blue Hazel Green
Black 36 9 5 2
Brown 66 34 29 14
Red 16 7 7 7
Blond 4 64 5 8
[1] 4 4 2
[1] TRUE
Data frame a matice mají stejný počet dimenzí; data frame tak můžeme indexovat stejným způsobem jako matici.
vek strana sex
SC_001 27 sin female
SC_007 35 sin male
SC_013 30 dx male
SC_014 47 dx female
SC_020 42 dx female
[1] "female"
[1] 42
vek strana sex
SC_001 27 sin female
SC_007 35 sin male
Data frame má narozdíl od matice ovšem jednu velkou výhodu; můžeme indexovat přímo pomocí jmen sloupců. Co to znamená?
Výběr celého sloupce znamená i výběr všech řádků
Proč zde nemusíme použít čárku? R defacto říkáme “vyber celý objekt jménem strana, včetně jeho struktury a pojmenování”. A celý sloupec strana obsahuje hodnoty pro každý řádek.
R automaticky usuzuje že data frame je poskládaný tak, že jednotlivá měření/vzorky/pozorování jsou zapsaná v řádcích, nikoliv ve sloupcích - jedná se o takzvaný long formát dat. To znamená, že usuzuje, že jednotlivé vektory, ze kterých se data frame skládá, budou sloupce.
Více o long formátu a proč je dobré ho používat si řekneme během příští lekce při probírání konceptu “tidy data”.
Možná si myslíte, že v tuto chvíli znáte veškeré základní způsoby indexace v base R. Na vše samozřejmě existují “vyjímky”.
strana
SC_001 sin
SC_007 sin
SC_013 dx
SC_014 dx
SC_020 dx
strana
SC_001 sin
SC_007 sin
SC_013 dx
SC_014 dx
SC_020 dx
[1] TRUE
Při výběru pouze jedné hodnoty u data frame R automaticky usoudí, že se jedná o výběr sloupce na této pozici.
strana
SC_001 sin
SC_007 sin
SC_013 dx
SC_014 dx
SC_020 dx
strana
SC_001 sin
SC_007 sin
SC_013 dx
SC_014 dx
SC_020 dx
[1] "sin" "sin" "dx" "dx" "dx"
vek strana
SC_001 27 sin
SC_007 35 sin
SC_013 30 dx
SC_014 47 dx
SC_020 42 dx
Proč nám výsledky vycházejí někdy jako vektor a jindy jako data frame?
Jak bylo zmíněno v sekci Výběr celého sloupce znamená i výběr všech řádků, výběrem sloupce vybíráme objekt, který tvoří data frame - nikoliv pouze hodnoty. R proto vrátí část data frame, včetně struktur, popisků a všeho - vrátí se nám proto data frame o jednom sloupci.
Když ovšem provedeme výběr definicí df[ ,"strana"], tak dochází k jinému pokynu. R totiž říkáme následující:
Vyber hodnoty v druhém sloupci, a to pro všechny řádky.
A co je výsledkem řady hodnot? Vektor.
Je ovšem možné přinutit R, aby si zachovalo původní data frame strukturu.
vek
SC_001 27
SC_007 35
SC_013 30
SC_014 47
SC_020 42
strana
SC_001 sin
SC_007 sin
SC_013 dx
SC_014 dx
SC_020 dx
Argument drop = FALSE nám totiž nuceně udrží i výběr takovéhoto typu jako data frame.
Nezapomeňte, že indexace je defacto typ funkce!
Provádíme akci na základě určitých parametrů, která provede změny na datech.
Podívejte se v nápovědě na funkci extract ;).
Proč nám při výběru hodnot z více sloupců a libovolného počtu řádku ovšem opět vznikne data frame?
vek strana
SC_007 35 sin
vek strana
SC_001 27 sin
SC_007 35 sin
SC_013 30 dx
SC_014 47 dx
SC_020 42 dx
Nápověda: výsledek nám může vrátit hodnoty různého datového typu
Nelze vrátit vektor, který obsahuje hodnoty v jiné podobě než jednodimenzionálně poskládané za sebou. Stejně tak matice nemůže obsahovat více data typů.
Jediným možným řešením je proto strukturovat data jako data frame.
Co znamená [[x]]?
Někdy se můžete setkat s tím, že údaj, pomocí kterého se indexuje, je zapsaný v dvojtých hranatých závorkách. Co to znamená?
[1] "sin" "sin" "dx" "dx" "dx"
[1] "sin" "sin" "dx" "dx" "dx"
Dvojité hranaté závorky nám říkají; vyber mi prvek x a vše, co se v něm nachází.
Jednotlivé prvky data frame jsou vektory, proto nám indexace vrátí vektor hodnot.
| Způsob indexace | Výsledek |
|---|---|
df[,"col"] |
vektor |
df[,"col",drop = FALSE] |
data frame |
df["col"] |
data frame |
df[["col"]] |
vektor |
df$col |
vektor |
Vyber první sloupec v data frame df jako vektor i data frame.
Vyber první a poslední řádek data frame df.
Při vytváření indexování specificky pojmenovaného sloupce se někdy používá symbol $.
[1] "sin" "sin" "dx" "dx" "dx"
[1] "sin" "sin" "dx" "dx" "dx"
symbol
$provede výběr hodnot ze specifické komponenty datové struktury podle jejího názvu
list/data frame ve kterém se hledá$název objektu, který ho tvoří
Jen tak ze zvědavosti, lze tento typ indexace použít i u matice?
Nápověda: jaká je definice data frame a matice?
Zatímco matice jsou defacto pouze hodnoty jednoho data typu poskládané do řádků a sloupců, které mohou být pojmenované, data frame je objekt složený z jiných objektů.
Jaká je struktura matice?
int [1:4, 1:6] 10 11 12 13 14 15 16 17 18 19 ...
- attr(*, "dimnames")=List of 2
..$ : chr [1:4] "A" "B" "C" "D"
..$ : chr [1:6] "a" "b" "c" "d" ...
Jaká je struktura data frame?
Kdykoliv, kdy potřebujeme pracovat s čistými hodnotami, nikoliv celou datovou strukturou.
Příkladem může být jak čistá indexace, ale i přepisování, nebo třeba i doplňování dalších hodnot.
Několik z možností si probereme v následující části.
Indexace
vek strana sex
SC_007 35 sin male
SC_014 47 dx female
SC_020 42 dx female
Jak to funguje? Totožně jako u jakékoliv jiné indexace; výběrem TRUE a FALSE hodnot.
[1] 27 35 30 47 42
[1] FALSE TRUE FALSE TRUE TRUE
vek strana sex
SC_007 35 sin male
SC_014 47 dx female
SC_020 42 dx female
vek strana sex
SC_007 35 sin male
SC_014 47 dx female
SC_020 42 dx female
Další možnost je například přepis hodnot.
vek strana sex
SC_001 27 leva female
SC_007 35 leva male
SC_013 30 dx male
SC_014 47 dx female
SC_020 42 dx female
Co se v tomto kódu provede?
[1] "leva" "leva" "dx" "dx" "dx"
[1] FALSE FALSE TRUE TRUE TRUE
[1] "dx" "dx" "dx"
vek strana sex
SC_001 27 leva female
SC_007 35 leva male
SC_013 30 prava male
SC_014 47 prava female
SC_020 42 prava female
Nakonec si vyzkoušíme i přiřazování dalších hodnot.
[1] 27 35 30 47 42 1 2 3 4 5 6 7 8 9 10
Přiřazováním ale můžeme i vytvářet celé další sloupce.
[1] 5 3
vek strana sex score
SC_001 27 leva female 1
SC_007 35 leva male 2
SC_013 30 prava male 3
SC_014 47 prava female 4
SC_020 42 prava female 5
[1] 5 4
Co jsme zde provedli?
dim(df): kolik dimenzí má df
1:nrow(df): vektor, který má v sobě tolik hodnot co df řádků
df$score <- 1:nrow(df): ulož vektor jako hodnoty ve sloupci score
Zkušební datasety v balíčku dplyr
V balíčku dplyr je nainstalováno několik datasetů určených k zkoušení si funkcí a celkovému hraní si, obdobně jako v baseR. Dataset storms, který budeme v následujícím procvičení používat, je právě jedním z nich. Pro jejich používání je potřeba mít balíček načtený. Dataset iris je součástí baseR.
wind) v roce, kdy jste se narodili (year)? Použijte dataset dplyr::storms.iris všechny měření, kdy délka kalichu květiny (Sepal.Length) je menší než 5, nebo jejich šířka (Sepal.Width) je větší než 3.5 a zároveň se jedná o druh (Species) setosa.Petal.Lenght) pro druh setosa, poté co jsme provedli filtrování v předchozím cvičení?Nahrajte si data uložená v souboru bikes.RData. Ten obsahuje přehled testování motorek, kdy každý stroj dostal určitý počet bodů za hodnocení rychlosti (speed), pohodlnosti na vzdálenost (dist) a pak ještě celkové hodnocení od nezávislého odborníka (rating), kdy 1 je nejlepší, 5 je nejhorší.
speed a dist sice celkem menší než 50, ale i tak dostaly rating lepší než 3. Vypište jejich názvy.Bonus: Přepiš hodnoty ve sloupci dist v tomto výběru tak, že pokud je hodnota menší jak 20, bude nahrazena slovy “pod dvacet”, pokud bude větší nebo rovno 20, bude nahrazena slovy “dvacet +”.
Vyberte motorky, které měli počet bodů z obou hodnocení dohromady sice menší než 50, ale i tak dostaly rating lepší než 3. Vypište jejich názvy.
Podíváme se na strukturu datového objektu bikes a necháme si vyjet prvních několik řádků. Vidíme, že se jedná o data frame, takže k vyhledávání můžeme používat přímo názvy sloupců.
Vyber ty řádky, kde součet z hodnot ve sloupcích speed a dist je < 50, a zároveň hodnota ve sloupci rating je < 3.
Pro snažší práci s tímto výběrem si ho pojmenujeme a uložíme.
Přepiš hodnoty ve sloupci dist v tomto výběru tak, že pokud je hodnota menší jak 20, bude nahrazena slovy “pod dvacet”, pokud bude větší nebo rovno 20, bude nahrazena slovy “dvacet +”.
Vybereme hodnoty ze sloupce dist které jsou < 20 a přepíšeme je na charaktery “pod dvacet”.
Podíváme se na to, jaká je nyní struktura sloupce dist.
Hodnoty se nuceně převedly na charaktery; není možné mít v jednom vektoru numeric a character hodnoty. Proto dále nemůžeme použít operátory > nebo <, ale použijeme místo toho operátory != aka “není přesně”.
Principy, které jsme se naučili na data frame, nyní můžeme použít k indexování listu.
$osoba
$osoba$jmeno
[1] "Anna"
$osoba$prijmeni
[1] "Novotná"
$povolani
[1] "uklizecka"
$vek
[1] 67
List of 3
$ osoba :List of 2
..$ jmeno : chr "Anna"
..$ prijmeni: chr "Novotná"
$ povolani: chr "uklizecka"
$ vek : num 67
Jakým způsobem si můžeme z listu vybrat jednotlivé jeho části?
$vek
[1] 67
List of 1
$ vek: num 67
[1] 67
num 67
[1] 67
num 67
$povolani
[1] "uklizecka"
$povolani
[1] "uklizecka"
$vek
[1] 67
Co když ale nevybíráme jednoduchou část listu, jako třeba vektor? Co když se jedná o další list?
$osoba
$osoba$jmeno
[1] "Anna"
$osoba$prijmeni
[1] "Novotná"
List of 1
$ osoba:List of 2
..$ jmeno : chr "Anna"
..$ prijmeni: chr "Novotná"
$jmeno
[1] "Anna"
$prijmeni
[1] "Novotná"
List of 2
$ jmeno : chr "Anna"
$ prijmeni: chr "Novotná"
$jmeno
[1] "Anna"
$prijmeni
[1] "Novotná"
List of 2
$ jmeno : chr "Anna"
$ prijmeni: chr "Novotná"
A co když nechceme vybrat pouze ten list, ale přímo hodnoty v něm?
Rozdíl mezi [[]] a $
Možná si říkáte, proč vůbec potřebujeme tyto dva druhy indexace. Nedělá to přeci jen to samé?
Důležité je se dívat na to, jakým způsobem vkládáme do indexace.
Přidejte paní Anně Novákové další povolání.
Přidejte informace o jejích dvou dětech; každé ve vlastním listu se jménem a příjmením, dohromady pak ve společném listu “deti”.
dplyrV tuto chvíli víme, na jakém principu funguje indexace v R, a s jakými symboly a způsoby provedení se můžete běžně setkat. Některé z těchto procesů indexace jsou ale dost krkolomné, nebo vyžadují od uživatele repetitivní psaní kódu.
Co kdyby existovalo něco… jednoduššího?
dplyr::selectVyber sloupce z data frame
select(název data frame, název sloupce)
speed
bike_01 4
bike_02 4
bike_03 7
bike_04 7
bike_05 8
bike_06 9
bike_07 10
bike_08 10
bike_09 10
bike_10 11
bike_11 11
bike_12 12
bike_13 12
bike_14 12
bike_15 12
bike_16 13
bike_17 13
bike_18 13
bike_19 13
bike_20 14
bike_21 14
bike_22 14
bike_23 14
bike_24 15
bike_25 15
bike_26 15
bike_27 16
bike_28 16
bike_29 17
bike_30 17
bike_31 17
bike_32 18
bike_33 18
bike_34 18
bike_35 18
bike_36 19
bike_37 19
bike_38 19
bike_39 20
bike_40 20
bike_41 20
bike_42 20
bike_43 20
bike_44 22
bike_45 23
bike_46 24
bike_47 24
bike_48 24
bike_49 24
bike_50 25
To nevypadá tak impresivně, že? Vždyť to si mohu napsat i jako bikes$speed…
Co když ale máte sloupců na výběr podstatně více?
tibble [20,778 × 13] (S3: tbl_df/tbl/data.frame)
$ name : chr [1:20778] "Amy" "Amy" "Amy" "Amy" ...
$ year : num [1:20778] 1975 1975 1975 1975 1975 ...
$ month : num [1:20778] 6 6 6 6 6 6 6 6 6 6 ...
$ day : int [1:20778] 27 27 27 27 28 28 28 28 29 29 ...
$ hour : num [1:20778] 0 6 12 18 0 6 12 18 0 6 ...
$ lat : num [1:20778] 27.5 28.5 29.5 30.5 31.5 32.4 33.3 34 34.4 34 ...
$ long : num [1:20778] -79 -79 -79 -79 -78.8 -78.7 -78 -77 -75.8 -74.8 ...
$ status : Factor w/ 9 levels "disturbance",..: 7 7 7 7 7 7 7 7 8 8 ...
$ category : num [1:20778] NA NA NA NA NA NA NA NA NA NA ...
$ wind : int [1:20778] 25 25 25 25 25 25 25 30 35 40 ...
$ pressure : int [1:20778] 1013 1013 1013 1013 1012 1012 1011 1006 1004 1002 ...
$ tropicalstorm_force_diameter: int [1:20778] NA NA NA NA NA NA NA NA NA NA ...
$ hurricane_force_diameter : int [1:20778] NA NA NA NA NA NA NA NA NA NA ...
# A tibble: 20,778 × 4
lat long year hurricane_force_diameter
<dbl> <dbl> <dbl> <int>
1 27.5 -79 1975 NA
2 28.5 -79 1975 NA
3 29.5 -79 1975 NA
4 30.5 -79 1975 NA
5 31.5 -78.8 1975 NA
6 32.4 -78.7 1975 NA
7 33.3 -78 1975 NA
8 34 -77 1975 NA
9 34.4 -75.8 1975 NA
10 34 -74.8 1975 NA
# ℹ 20,768 more rows
# A tibble: 20,778 × 7
name year month day wind hour hurricane_force_diameter
<chr> <dbl> <dbl> <int> <int> <dbl> <int>
1 Amy 1975 6 27 25 0 NA
2 Amy 1975 6 27 25 6 NA
3 Amy 1975 6 27 25 12 NA
4 Amy 1975 6 27 25 18 NA
5 Amy 1975 6 28 25 0 NA
6 Amy 1975 6 28 25 6 NA
7 Amy 1975 6 28 25 12 NA
8 Amy 1975 6 28 30 18 NA
9 Amy 1975 6 29 35 0 NA
10 Amy 1975 6 29 40 6 NA
# ℹ 20,768 more rows
dplyr::filterVyber řádky na základě podmínky
filter(název data frame, podmínky hodnot ve sloupcích)
# A tibble: 45 × 13
name year month day hour lat long status category wind pressure
<chr> <dbl> <dbl> <int> <dbl> <dbl> <dbl> <fct> <dbl> <int> <int>
1 Georges 1980 9 1 0 15.6 -38 tropical… NA 30 1010
2 Georges 1980 9 1 6 15.9 -39.4 tropical… NA 30 1010
3 Georges 1980 9 1 12 16.3 -40.8 tropical… NA 30 1010
4 Georges 1980 9 1 18 16.8 -42.1 tropical… NA 30 1010
5 Georges 1980 9 2 0 17.3 -43.7 tropical… NA 30 1010
6 Georges 1980 9 2 6 17.5 -45.7 tropical… NA 30 1010
7 Georges 1980 9 2 12 17.7 -48.1 tropical… NA 30 1010
8 Georges 1980 9 2 18 17.8 -50.3 tropical… NA 30 1010
9 Georges 1980 9 3 0 17.9 -52.4 tropical… NA 30 1010
10 Georges 1980 9 3 6 18 -54.5 tropical… NA 30 1010
# ℹ 35 more rows
# ℹ 2 more variables: tropicalstorm_force_diameter <int>,
# hurricane_force_diameter <int>
A co kdybychom to spojili dohromady?
# A tibble: 3 × 13
name year month day hour lat long status category wind pressure
<chr> <dbl> <dbl> <int> <dbl> <dbl> <dbl> <fct> <dbl> <int> <int>
1 Allison 1995 6 4 12 24.7 -86.2 hurricane 1 65 987
2 Allison 1995 6 4 18 26.2 -86.2 hurricane 1 65 988
3 Allison 1995 6 5 0 27.6 -86.1 hurricane 1 65 988
# ℹ 2 more variables: tropicalstorm_force_diameter <int>,
# hurricane_force_diameter <int>
# A tibble: 3 × 3
name year wind
<chr> <dbl> <int>
1 Allison 1995 65
2 Allison 1995 65
3 Allison 1995 65
Stáhněte si data, které budou přiloženy u lekce ve výukových materiálech. Nezapomeňte si je uložit do dedikované složky, žádné “najdu to ve stažených souborech”!
V příští lekci budeme pracovat s nahráváním dat a s projekty, proto je opravdu potřeba v tom mít pořádek.
Vyber z následujícího vektoru každou pátou hodnotu
[1] 15.20 15.76 16.32 16.88 17.44 18.00 18.56 19.12 19.68 20.24 20.80 21.36
[13] 21.92 22.48 23.04 23.60 24.16 24.72 25.28 25.84 26.40 26.96 27.52 28.08
[25] 28.64 29.20 29.76 30.32 30.88 31.44 32.00 32.56 33.12 33.68 34.24 34.80
[37] 35.36 35.92 36.48 37.04 37.60 38.16 38.72 39.28 39.84 40.40 40.96 41.52
[49] 42.08 42.64 43.20 43.76 44.32 44.88 45.44
Z datasetu (co je nahraný v R) jménem airquality, který obsahuje informace o měření kvality vzduchu v NYC, vyber hodnoty ze sloupce Temp z prvního týdne v květnu.
K datasetu airquality přidejte nový sloupec s názvem Weather který bude obsahovat informaci (text hot), zda hodnoty ve sloupci Temp jsou vyšší než 70. Pokud není vyšší jako 70, bude obsahovat text cold.
Bonus: Pokuste se zjistit, jak si v nápovědě můžete najít seznam nahraných datasetů v R (iris, cars, dplyr::starwars a jiné)
Skript s výpočtem zašlete nejpozději do pátku před příští hodinou na lucie.hoskova@ruk.cuni.cz