-
Notifications
You must be signed in to change notification settings - Fork 4
Expand file tree
/
Copy path04-plotting_ggplotting.Rmd
More file actions
229 lines (171 loc) · 8.51 KB
/
04-plotting_ggplotting.Rmd
File metadata and controls
229 lines (171 loc) · 8.51 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
# Plotando
## `plot` (base)
**Exemplo**: Dados de qualidade do ar
```{r}
df <- readRDS("dados/df.rds")
summary(df)
```
A função `plot` precisa dos seguintes argumentos:
```{r}
args(plot)
```
Então, a forma mais fácil de plotar uma variável em função do tempo é:
```{r}
plot(x = df$tempo, y = df$MediaHoraria)
```
Feio, né?
Tentando deixar mais bonito...
```{r}
plot(x = df$tempo[1:100], y = df$MediaHoraria[1:100], #-- Selecionando uma parte do df!
pch = 16, #-- Forma do ponto (círculo preenchido)
type = "b", #-- Tipo de gráfico ("b" = both, ponto e linha)
col = "blue", #-- Cor do elemento (definido pelo type)
xlab = "Data", ylab = "NOx [ppb]", #-- Nome dos eixos x e y
main = "Gráfico mais Bonito") #-- Título do gráfico
```
Colocando **DOIS** elementos no mesmo gráfico:
<a id="plot_base"></a>
```{r}
df_parcial <- df[1:180,] #-- Selecionando uma parte do df!
plot(x = df_parcial$tempo[df_parcial$Valido == "Sim"],
y = df_parcial$MediaHoraria[df_parcial$Valido == "Sim"],
pch = 16, type = "b", col = "blue",
xlab = "Data", ylab = "NOx [ppb]",
main = "Dados Válidos e Inválidos")
lines(x = df_parcial$tempo[df$Valido == "Não"],
y = df_parcial$MediaHoraria[df$Valido == "Não"],
pch = 15, type = "b", col = "red")
```
***
<span style="color:purple">**Desafio**: Coloque uma legenda na figura especificando que os dados válidos estão em azul e os inválidos em vermelho </span>
***
A função `plot` cumpre bem o papel de gerar um gráfico simples, e até permite algumas customizações, mas ela exige cada vez mais linhas de código e argumentos dentro das funções para deixar o gráfico "mais bonito" - ao cumprir o desafio, você irá perceber como uma coisa "simples" como colocar uma legenda pode exigir muito mais do que parece!
## image
A função `image` permite pĺotear matrieces diretamente. Vamos testar esta função
com a librería `cptcity`. Argumentos similares de plot podem ser usados em
`image`.
```{r}
library(cptcity)
image(matrix(1:100), col = lucky())
image(matrix(1:100), col = lucky())
image(matrix(1:100), col = lucky())
```
## `ggplot` (ggplot2)
A função `ggplot` funciona de um jeito um pouco diferente. Veja a figura abaixo:

Em vez de uma única função, o gráfico é formado por camadas, sendo que cada camada é um elemento (`geom_...` ou `stat_...`) ou configuração (`scale_..._...`, `coord_...`, `theme` ou `theme_...`, `guides`, `labs`, etc). Consulte a maioria das opções disponíveis em [Data Visualization Cheatsheet](https://github.com/rstudio/cheatsheets/raw/master/data-visualization-2.1.pdf).
Que tal refazermos os gráficos da seção anterior?
```{r, message=FALSE}
#-- Não esqueça de carregar o pacote!
library(ggplot2)
```
```{r}
ggplot(df, aes(x = tempo, y = MediaHoraria)) +
geom_point(pch = 1)
```
```{r}
ggplot(df[1:100,], aes(x = tempo, y = MediaHoraria)) +
geom_line(color = "blue") + #-- Linhas...
geom_point(color = "blue", pch = 16) + #-- ... com pontos
labs(title = "Gráfico mais Bonito", x = "Data", y = "NOx [ppb]") + #-- Títulos
theme(plot.title = element_text(hjust = 0.5)) #-- Centralizando o título
```
Agora o mais interessante:
```{r}
ggplot(df[1:180,], aes(x = tempo, y = MediaHoraria)) +
geom_line(aes(color = Valido)) +
geom_point(aes(color = Valido, shape = Valido)) +
labs(title = "Dados Válidos e Inválidos", x = "Data", y = "NOx [ppb]") +
scale_color_manual(values = c("red", "blue")) + #-- Definindo as cores manualmente
scale_shape_manual(values = c(15, 16)) + #-- Definindo as formas manualmente
theme(plot.title = element_text(hjust = 0.5))
```
<span style="color:blue">**Pergunta**: Qual a principal diferença entre o código acima e o [código usando `plot`](#plot_base)?</span>
A função `ggplot` plota apenas data frames, pois ela mapeia as variáveis por nomes de colunas. Assim, é preciso [converter matrizes ou arrays em data frames](#convert_df).
Uma vantagem de trabalharmos com data frames, [como já vimos antes](#processing_dfs), é poder manipular esses dados de muitas formas possíveis antes de plotá-los.
**Continuação do Exemplo**: Extraindo algumas informações sobre os dados
Vamos analisar o ano de 2014:
* *Em média*, como o NOx varia ao longo do dia?
+ E para cada dia da semana?
+ E para cada mês?
Usando algumas outras funções dentro do [**Tidyverse**](#tidyverse):
```{r, message=FALSE}
library(tidyverse)
df_2014 <- filter(df, ano == "2014")
df_2014_hour <- df_2014 %>% #-- A partir do data frame df_2014
group_by(Hora) %>% #-- Agrupe os dados pela coluna hora
summarise(Media = mean(MediaHoraria, na.rm = T)) %>% #-- E calcule as médias,
#-- salvando em uma coluna nova
mutate(Hora = as.POSIXct(strptime(Hora, "%H:%M"))) %>% #-- Transformando em data
ungroup() #-- Desagrupando
ggplot(df_2014_hour) +
scale_x_datetime(date_labels = "%H:%M") + #-- Formato de data que aparecerá no eixo x
geom_line(aes(x = Hora, y = Media, group = 1), color = "purple") +
labs(title = "Média Horária Anual", y = "NOx [ppb]")
```
```{r, message=FALSE}
df_2014_weekly <- df_2014 %>%
group_by(Hora, weekdays) %>% #-- Agrupando os dados pelas colunas Hora e weekdays
summarise(Media = mean(MediaHoraria, na.rm = T)) %>%
ungroup() %>%
mutate(Hora = as.POSIXct(strptime(Hora, "%H:%M"))) %>%
mutate(weekdays = factor(weekdays, levels = c("segunda", "terça", "quarta",
"quinta", "sexta", "sábado",
"domingo"))) #-- Ordenando os dias da semana
ggplot(df_2014_weekly) +
scale_x_datetime(date_labels = "%H:%M") +
geom_col(aes(x = Hora, y = Media), fill = "purple") +
labs(title = "Média Horária Anual por Dia da Semana", y = "NOx [ppb]") +
facet_wrap(~ weekdays) #-- Criando paineis em função do dia da semana
```
```{r, message=FALSE}
df_2014_monthly <- df_2014 %>%
group_by(Hora, mes) %>% #-- Agrupando os dados pelas colunas Hora e mes
summarise(Media = mean(MediaHoraria, na.rm = T)) %>%
ungroup() %>%
mutate(Hora = as.POSIXct(strptime(Hora, "%H:%M"))) %>%
mutate(mes = factor(mes, levels = c("janeiro", "fevereiro", "março",
"abril", "maio", "junho", "julho",
"agosto", "setembro", "outubro",
"novembro", "dezembro"))) #-- Ordenando os meses
ggplot(df_2014_monthly) +
scale_x_datetime(date_labels = "%H:%M") +
geom_col(aes(x = Hora, y = Media), fill = "purple") +
labs(title = "Média Horária Anual por Mes", y = "NOx [ppb]") +
facet_wrap(~ mes) #-- Criando paineis em função do mês
```
***
<span style="color:red">**Exercício**: *Em média*, como **os dados válidos** de NOx variam mensalmente ao longo do ano de 2014? Faça um gráfico.</span>
<span style="color:purple">**Desafio**: Ainda é possível melhorar os gráficos acima! Pesquise como:</span>
<span style="color:purple">* Diminuir a quantidade de horários no eixo x</span>
<span style="color:purple">* Separar por dias da semana e meses a partir da coluna "tempo", não precisando usar as colunas de caracteres e consequentemente ordená-las manualmente</span>
***
### Explorando outras escalas de cores e temas
Pacotes **veinreport** e **cptcity**
```{r eval=F}
devtools::install_github("atmoschem/veinreport")
```
```{r message=F}
library(veinreport)
library(cptcity)
```
Refazendo alguns gráficos:
```{r}
ggplot(df, aes(x = tempo, y = MediaHoraria)) +
geom_line(aes(color = MediaHoraria)) +
labs(x = "Data", y = "NOx [ppb]") +
scale_color_gradientn(colours = cpt()) + #-- Definindo as cores com uma escala gradiente
theme_black()
```
Experimentando escalas de cores com a função `lucky`:
```{r}
ggplot(df_2014_monthly) +
scale_x_datetime(date_labels = "%H:%M") +
geom_col(aes(x = Hora, y = Media, fill = Media)) +
labs(title = "Média Horária Anual por Mes", y = "NOx [ppb]") +
scale_fill_gradientn(colors = lucky()) + #-- Definindo as cores com uma escala gradiente aleatória
theme_black() +
theme(legend.position = "bottom", legend.direction = "horizontal") + #-- Colocando a legenda na parte de baixo da figura
facet_wrap(~ mes) #-- Criando paineis em função do mês
```
**Este é só o começo!** [Veja aqui um pouco mais das muitas aplicações do `ggplot`](http://r-statistics.co/Top50-Ggplot2-Visualizations-MasterList-R-Code.html).