1 Line

Trong nhóm biểu đồ line gồm có 3 kiểu đồ thị chính là geom_line(), geom_path() và geom_step(). Trong đó geom_line() là phổ biến nhất biểu diễn mối quan hệ giữa x,y theo thứ tự của trục x từ bé đến lớn. geom_path() thì khác biết hơn, trước khi biểu diễn đồ thị nó sẽ không sort x mà giữ nguyên vị trí các quan sát (x,y) như trong dataframe. Do đó dẫn đến đồ thị sẽ không smoothing như geom_line(). geom_step() là độ thị dạng bậc thang nhấn mạnh sự thay đổi của y theo x theo thứ tự của x.

Cú pháp

geom_path(mapping = NULL, data = NULL, stat = "identity",
  position = "identity", ..., lineend = "butt", linejoin = "round",
  linemitre = 1, arrow = NULL, na.rm = FALSE, show.legend = NA,
  inherit.aes = TRUE)

geom_line(mapping = NULL, data = NULL, stat = "identity",
  position = "identity", na.rm = FALSE, show.legend = NA,
  inherit.aes = TRUE, ...)

geom_step(mapping = NULL, data = NULL, stat = "identity",
  position = "identity", direction = "hv", na.rm = FALSE,
  show.legend = NA, inherit.aes = TRUE, ...)

Giải thích các Arguments

  • mapping: Thiết lập các trục x,y thông qua aes.
  • data: data.frame được sử dụng visualize. Nếu để NULL thì sẽ lấy từ hàm liền trước là ggplot(). Data bắt buộc phải có định dạng data.frame.
  • stat: Biến đổi thống kê sử dụng trong dữ liệu để vẽ đồ thị.
  • position: Điều chỉnh vị trí của đồ thị.
  • …: Những argument khác được pass vào đồ thị. Thông thường là các giá trị qui định về color, size của đồ thị.
  • show.legend: Có thể hiện legend hay không. Mặc định là show.legend trong trường hợp các trục được mapping thông qua hàm aes().
  • direction: Hướng của đồ thị bậc thang gồm 2 giá trị ‘vh’ nếu vertical và ‘hv’ nếu horizontal.
library(ggplot2)
library(VNDS)
library(dplyr)
library(reshape)
library(rlang)
VND <- getSymbols('VND', '2017-01-01', '2018-04-25')
## #VND from 2017-01-01 to 2018-04-25 already cloned
SSI <- getSymbols('SSI', '2017-01-01', '2018-04-25')
## Note: no visible binding for global variable '.' 
## #SSI from 2017-01-01 to 2018-04-25 already cloned
#Vẽ biểu đồ geom_line của VND
ggplot(data = VND) +
  geom_line(aes(DATE, CLOSE)) +
#Định dạng scale cho time
  scale_x_date(date_breaks = '2 month', date_labels = '%Y-%m')

#Vẽ đồ thị geom_line cho VND và SSI  
VND <- VND %>% select(DATE,VND = CLOSE)
SSI <- SSI %>% select(DATE,SSI = CLOSE)
inner_join(SSI,VND, by='DATE') %>% melt(id="DATE") %>% 
  ggplot(aes(x=DATE,y=value,colour=variable)) + geom_line()

#Vẽ biểu đồ step()
recent <- VND %>% filter(DATE >= '2018-02-01' )
ggplot(recent, aes(DATE, VND)) + geom_step()

#Để biểu diễn mối quan hệ giữa VND và SSI qua thời gian chúng ta sẽ sử dụng geom_path()
inner_join(SSI,VND, by='DATE') %>% 
  ggplot(aes(x=VND,y=SSI)) + geom_path()

#Thêm scale màu sắc
inner_join(SSI,VND, by='DATE') %>% 
  ggplot(aes(x=VND,y=SSI)) + geom_path(aes(colour = as.numeric(DATE)))

#Thêm arrow
VND %>% ggplot(aes(x=DATE,y=VND)) + geom_line(
  arrow = arrow(angle = 15, ends = "both", type = "closed")
) 

#Thay đổi kiểu line
VND %>% ggplot(aes(x=DATE,y=VND)) + geom_line(
  linetype=2
) + 
labs(x = 'Week in year',
     y = 'Price') +
scale_x_date(date_breaks = '2 week', date_labels = '%W')

#Kết hợp geom_line và geom_point
VND %>% ggplot(aes(x=DATE,y=VND)) + geom_line() + geom_point()

2 Point

Được sử dụng để tạo ra các biểu đồ dạng scatterplot. Đây là biểu đồ chuyên dùng để biểu diễn mối quan hệ giữa 2 biến liên tục.

Cú pháp

geom_point(mapping = NULL, data = NULL, stat = "identity",
  position = "identity", ..., na.rm = FALSE, show.legend = NA,
  inherit.aes = TRUE)

Giải thích các arguments

Tương tự như các argument của geom_line

Các thành phần của trục

  • x,y: Trục tung và hoành

  • alpha: Độ trong suốt

  • colour: Màu sắc

  • fill: Màu sắc bên trong trong trường hợp có viền bao ngoài

  • group: Các nhóm

  • shape: Hình dạng của point

  • size: Kích thước điểm

  • stroke: Kích thước viền

#Biểu diễn đồ thị geom_point mối quan hệ của Sepal.Length và Sepal.Width.
p <- ggplot(iris, aes(Sepal.Length,Sepal.Width))
p + geom_point()

#Thêm màu sắc theo nhóm Species
p + geom_point(aes(colour = Species))

## Note: no visible binding for global variable 'R' 
## Note: no visible binding for global variable 'R' 
## Note: no visible binding for global variable 'R' 
## Note: no visible binding for global variable 'R' 
## Note: no visible binding for global variable 'R' 
## Note: no visible binding for global variable 'R' 
## Note: no visible binding for global variable 'R' 
## Note: no visible binding for global variable 'R' 
## Note: no visible binding for global variable 'R' 
## Note: no visible binding for global variable 'R' 
## Note: no visible binding for global variable 'R' 
## Note: no visible binding for global variable 'R' 
## Note: no visible binding for global variable 'R' 
## Note: no visible binding for global variable 'R' 
## Note: no visible binding for global variable 'R' 
## Note: no visible binding for global variable 'R' 
## Note: no visible binding for global variable 'key.row' 
## Note: no visible binding for global variable 'key.col' 
## Note: no visible binding for global variable 'label.row' 
## Note: no visible binding for global variable 'label.col' 
## Note: no visible binding for global variable 'key.row' 
## Note: no visible binding for global variable 'key.col' 
## Note: no visible binding for global variable 'label.row' 
## Note: no visible binding for global variable 'label.col' 
## Note: no visible binding for global variable 'key.row' 
## Note: no visible binding for global variable 'key.col' 
## Note: no visible binding for global variable 'label.row' 
## Note: no visible binding for global variable 'label.col' 
## Note: no visible binding for global variable 'key.row' 
## Note: no visible binding for global variable 'key.col' 
## Note: no visible binding for global variable 'label.row' 
## Note: no visible binding for global variable 'label.col'
#Thay đổi shape theo nhóm Species
p + geom_point(aes(shape = Species))

#Điều chỉnh kích cỡ theo quintile
p + geom_point(aes(size = Petal.Length))

#Thay đổi scale
p + geom_point(aes(colour = Petal.Length)) + scale_colour_gradient(low='blue')

p + geom_point(aes(shape = Species)) + scale_shape(solid = FALSE)

#Thay đổi màu sắc và point
p + geom_point(aes(shape = Species), colour = 'red', size = 2)

#Tạo ra 2 layer lồng nhau, một layer size lơn hơn tạo viền bao ngoài cho layer bên trong
p + geom_point(colour = 'black', size = 4.5) + 
  geom_point(colour = 'pink', size = 4) + 
  geom_point(aes(shape = factor(Species)))

3 Histogram

Đây là biểu đồ phổ biến trong thống kê mô tả, được sử dụng để visualization các biến liên tục để xem sự phân phối tần suất của các biến này theo từng bin có độ rộng gần bằng. Trong ggplot2 có 2 method có thể thực hiện chức năng của đồ thị histogram gồm geom_histogram() biểu diễn tần suất theo barchart và geom_freqpoly() biểu diễn tần suất theo dạng line. geom_freqpoly() thích hợp với các biến category và geom_histogram() thích hợp với biến liên tục, category đều được. Ngoài ra còn có stat_bin() ít được sử dụng hơn. Method này phù phợp với biến liên tục theo trục x, tuy nhiên x phân tán thì sử dụng stat_bin() là hợp lý nhất.

Cú pháp

geom_freqpoly(mapping = NULL, data = NULL, stat = "bin",
  position = "identity", ..., na.rm = FALSE, show.legend = NA,
  inherit.aes = TRUE)

geom_histogram(mapping = NULL, data = NULL, stat = "bin",
  position = "stack", ..., binwidth = NULL, bins = NULL, na.rm = FALSE,
  show.legend = NA, inherit.aes = TRUE)

stat_bin(mapping = NULL, data = NULL, geom = "bar", position = "stack",
  ..., binwidth = NULL, bins = NULL, center = NULL, boundary = NULL,
  breaks = NULL, closed = c("right", "left"), pad = FALSE,
  na.rm = FALSE, show.legend = NA, inherit.aes = TRUE)

Giải thích các Arguments

  • mapping: Sử dụng để mapping các trục trong lệnh aes(). Giá trị mặc định sẽ là inherit.aes = TRUE, đồ thị sẽ mapping giá trị các trục theo mặc định.

  • data: Dữ liệu sử dụng để visualization. Data nhất định phải có định dạng data.frame và có thể qui định trong geom_line() hoặc ggplot().

  • position: Điều chỉnh vị trí của đồ thị.

  • …: Thành phần bất kì nào khác được truyền vào model thông thường là các argument qui định size, và color.

  • na.rm: Mặc định là FALSE. Nếu là TRUE thì các quan sát có giá trị missing sẽ bị remove.

  • show.legend: Có show legend trong đồ thị hay không? mặc định là NA tức là nếu bất kì trục nào được map thì sẽ luôn show legend; TRUE luôn luôn show legend và FALSE không show legend.

  • binwidth: Độ rộng của các bins sử dụng để tính frequency.

  • bins: Số lượng bins sử dụng. Mặc định là 30.

  • center: Xác định center của 1 bin.

#Vẽ biểu đồ histogram của VND
VND %>% ggplot(aes(VND)) + geom_histogram()

#Thay đổi độ rộng của 1 bins bằng bindwidth
VND %>% ggplot(aes(VND)) + geom_histogram(binwidth = 0.2)

#Thay đổi số lượng bins
VND %>% ggplot(aes(VND)) + geom_histogram(bins = 15)

#Vẽ biểu đồ stacking histogram
inner_join(SSI,VND, by='DATE') %>% melt(id="DATE") %>% 
  ggplot(aes(value,fill=variable)) + geom_histogram()

#Vẽ biểu đồ dạng frequency polygons (dạng line)
inner_join(SSI,VND, by='DATE') %>% melt(id="DATE") %>% 
  ggplot(aes(value,colour=variable)) + geom_freqpoly()

#So sánh density với freqpoly
inner_join(SSI,VND, by='DATE') %>% melt(id="DATE") %>% 
  ggplot(aes(value,..density..,colour=variable)) + geom_freqpoly(binwidth=30)

#Vẽ histogram cho nhiều category trên cùng một facet
inner_join(SSI,VND, by='DATE') %>% melt(id="DATE") %>% 
  ggplot(aes(value, fill = variable)) + geom_histogram(bins = 40) +
  facet_wrap(~variable)

4 Density

Cũng tương tự như histogram, density tính mật độ xác xuất của các biến theo các kernel. Giá trị của trục tung được biểu diễn trong density là xác xuất thay vì số lượng như histogram và đường curve của density phải đảm bảo tổng diện tích nằm bên dưới nó bằng 1.

Cú pháp

geom_density(mapping = NULL, data = NULL, stat = "density",
  position = "identity", ..., na.rm = FALSE, show.legend = NA,
  inherit.aes = TRUE)

stat_density(mapping = NULL, data = NULL, geom = "area",
  position = "stack", ..., bw = "nrd0", adjust = 1, kernel = "gaussian",
  n = 512, trim = FALSE, na.rm = FALSE, show.legend = NA,
  inherit.aes = TRUE)

Giải thích các Arguments

Các arguments tương tự như histogram và có thêm một số argument như sau:

  • bw: làm smoothing bandwidth.

  • adjust: Điều chỉnh lại độ rộng bandwidth

  • kernel: Kernel sử dụng để tính density.

  • n: Số lượng điểm không gian bằng nhau mà hàm mật độ được ước lượng.

  • trim: Biểu diễn nhiều densities trên một plot. Nếu FALSE (mặc định) thì density được tính trên toàn bộ range của dữ liệu và trái lại nếu TRUE thì density được tính trên range của từng group.

#Vẽ biểu đồ density của VND
VND %>% ggplot(aes(VND)) + geom_density()

#Điều chỉnh lại độ rộng bandwidth bằng 1/2 so với mặc định
VND %>% ggplot(aes(VND)) + geom_density(adjust = 1/2)

## Note: no visible binding for global variable 'x' 
## Note: no visible binding for global variable 'x' 
## Note: no visible binding for global variable 'ymax' 
## Note: no visible binding for global variable 'ymin'
#Điều chỉnh độ rộng bandwidth lên gấp 2 lần so với mặc định
VND %>% ggplot(aes(VND)) + geom_density(adjust = 2)

#Biểu diễn nhiều density theo các category
inner_join(SSI,VND, by="DATE") %>% melt(id="DATE") %>% 
  ggplot(aes(value, colour=variable)) + 
  geom_density() +
  xlim(15,35)

#Thêm màu bên dưới các density với độ trong suốt alpha=0.5
inner_join(SSI,VND, by="DATE") %>% melt(id="DATE") %>% 
  ggplot(aes(value, fill=variable,colour=variable)) + 
  geom_density(alpha=0.5) +
  xlim(15,35)

#Điều chỉnh vị trí các đường density sao cho chúng stack lên nhau
inner_join(SSI,VND, by="DATE") %>% melt(id="DATE") %>% 
  ggplot(aes(value, fill=variable,colour=variable)) + 
  geom_density(alpha=0.5, position = 'stack') +
  xlim(15,35)

#Chuyển từ density sang count của histogram
inner_join(SSI,VND, by="DATE") %>% melt(id="DATE") %>% 
  ggplot(aes(value, ..count.. ,fill=variable,colour=variable)) + 
  geom_density(alpha=0.5, position = 'stack') +
  xlim(15,35)

#Chuyển sang dạng density  area bằng position='fill', trục tung biểu diễn tỷ lệ phần trăm mỗi category chiếm
inner_join(SSI,VND, by="DATE") %>% melt(id="DATE") %>% 
  ggplot(aes(value,fill=variable,colour=variable)) + 
  geom_density(alpha=0.5, position = 'fill') +
  xlim(15,35)

5 Boxplot

Biểu diễn phân phối của các điểm liên tục. Nó visualize 5 thống kê quan trọng gồm (median, 2 điểm hinges và 2 điểm whiskers).

Cú pháp

geom_boxplot(mapping = NULL, data = NULL, stat = "boxplot",
  position = "dodge", ..., outlier.colour = NULL, outlier.color = NULL,
  outlier.fill = NULL, outlier.shape = 19, outlier.size = 1.5,
  outlier.stroke = 0.5, outlier.alpha = NULL, notch = FALSE,
  notchwidth = 0.5, varwidth = FALSE, na.rm = FALSE, show.legend = NA,
  inherit.aes = TRUE)

stat_boxplot(mapping = NULL, data = NULL, geom = "boxplot",
  position = "dodge", ..., coef = 1.5, na.rm = FALSE, show.legend = NA,
  inherit.aes = TRUE)

Giải thích arguments

  • mapping, data, position,…: Tương tự như trên

  • outlier.colour: Trục mặc định cho outlie. Mặc định là NULL sẽ kế thừa từ trục sử dụng cho box.

  • notchwidth: Độ rộng của notch tương đối với body (mặc định là 0.5)

  • na.rm: Loại bỏ các giá trị null.

Các thành phần của trục

  • x: Trục hoành

  • lower, upper, middle: Giá trị thấp nhất, cao nhất và giá trị ở giữa của hinge (khung) tương ứng với các mức phân vị 25%, 75% và 50% của chuỗi theo quantile

  • notchlower, notchupper: lower và upper edge của notch = \(median - 1.58*IQR/sqrt(n)\)

  • ymin, ymax: Giá trị min, max của lower whisker (rìa). Giá trị nhỏ nhất lớn hơn hoặc bằng giá trị lower hinge (khung) \(- 1.5 * IQR\)

  • alpha, colour, fill: Lần lượt là độ trong suốt, màu sắc của nến và của đường viền.

  • group: Nhóm

  • linetype, shape, size, weight: Kiểu đồ thị của nến

Giải thích qua một chút về IQR (interquartile range): Là một chỉ số đặc trưng trong thống kê mô tả đo lường mức độ phân tán của chuỗi, có giá trị bằng mức phân vị thứ 75% - mức phân vị thứ 25% hay nói cách khác bằng upper nến - lower nến. Nếu kí hiệu các mức phân vị theo tứ phân vị (quantile) lần lượt là \(Q1, Q2, Q3, Q4\) thì upper nến = Q3; lower nến = Q1; \(IQR = Q3-Q1\). Các điểm outlier cũng được xác định theo IQR nếu như giá trị của nó nằm ngoài khoảng < \(Q1-1.5*IQR\) hoặc >\(Q2-1.5*IQR\)

#Biểu diễn boxplot của Sepal.Length theo loài trong iris
p <- ggplot(iris, aes(x=Species,y=Sepal.Length))
p + geom_boxplot()

## Note: no visible binding for global variable 'weight' 
## Note: no visible binding for global variable 'xend' 
## Note: no visible binding for global variable 'yend' 
## Note: no visible binding for global variable 'x' 
## Note: no visible binding for global variable 'y' 
## Note: no visible binding for global variable 'xmin' 
## Note: no visible binding for global variable 'xmax' 
## Note: no visible binding for global variable 'y' 
## Note: no visible binding for global variable 'size'
#Thêm geom_jitter() thể hiện sự biến động ngẫu nhiên tại mỗi point
p + geom_boxplot() + geom_jitter(width = 0.2)

#Xoay ngang biểu đồ
p + geom_boxplot() + coord_flip()

#Thêm notch
p + geom_boxplot(notch = TRUE)

#Thay đổi shape cho outlier
p + geom_boxplot(outlier.color = 'blue', outlier.shape = 1)

#Thay đổi màu sắc đường viền
p + geom_boxplot(aes(colour = Species))

#Thay đổi màu sắc fill thân nến
p + geom_boxplot(aes(fill = Species),colour = 'black') 

6 Candle chart

Trong ggplot2 không hỗ trợ đồ thị Candel chart. Tuy nhiên bằng cách này hay cách khác chúng ta vẫn có thể tạo ra được những biểu đồ candle chart theo ý muốn.

VPB <- getSymbols('VPB', from = '2017-10-01', to = '2018-04-29')
## #VPB from 2017-10-01 to 2018-04-29 already cloned
VPB <- VPB[,c("DATE","OPEN","CLOSE","HIGH","LOW")]

ggplot(VPB, aes(DATE)) + 
  geom_linerange(aes(ymin = LOW, ymax = HIGH)) +
  geom_rect(aes(xmin = DATE - 1/2*0.9, xmax = DATE + 1/2*0.9,
                ymin = OPEN, ymax = CLOSE, fill = ifelse(CLOSE <= OPEN, "down","up"))) +
  scale_fill_manual(labels = c("up","down"), values = c("darkgreen", "darkred")) + 
  guides(fill = FALSE, colour = FALSE) +
  scale_x_date(date_breaks = '1 month', date_labels = '%Y-%m-%d')

#Viết thành hàm tổng quát
candleChart <- function(data, width, colour,date_breaks = '1 month', date_labels = '%Y-%m-%d',...){
  p <- ggplot(data, aes(DATE)) + 
  geom_linerange(aes(ymin = LOW, ymax = HIGH)) +
  geom_rect(aes(xmin = DATE - 1/2*width, xmax = DATE + 1/2*width,
                ymin = OPEN, ymax = CLOSE, fill = ifelse(CLOSE >= OPEN, "down","up"))) +
  scale_fill_manual(labels = c("up","down"), values = colour) + 
  guides(fill = FALSE, colour = FALSE) +
  scale_x_date(date_breaks = date_breaks, date_labels = date_labels)
  if(any(data$OPEN == data$CLOSE)) 
    p <- p + geom_segment(data = subset(data, OPEN == CLOSE),
                          aes(x = DATE - 1/2*width, xend = DATE + 1/2*width, 
                          y = CLOSE, yend = CLOSE))
  p
}


FPT <- getSymbols('FPT', from = '2018-01-01', to = '2018-04-29')
## #FPT from 2018-01-01 to 2018-04-29 already cloned
#Đỏ là tăng, đỏ đậm là giảm
candleChart(data=FPT,width=0.9,colour=c('red','darkred'),date_breaks = '2 week', date_labels = '%Y-%m-%d')
## Note: no visible binding for global variable 'DATE' 
## Note: no visible binding for global variable 'LOW' 
## Note: no visible binding for global variable 'HIGH' 
## Note: no visible binding for global variable 'DATE' 
## Note: no visible binding for global variable 'DATE' 
## Note: no visible binding for global variable 'OPEN' 
## Note: no visible binding for global variable 'CLOSE' 
## Note: no visible binding for global variable 'CLOSE' 
## Note: no visible binding for global variable 'OPEN' 
## Note: no visible binding for global variable 'OPEN' 
## Note: no visible binding for global variable 'CLOSE' 
## Note: no visible binding for global variable 'DATE' 
## Note: no visible binding for global variable 'DATE' 
## Note: no visible binding for global variable 'CLOSE' 
## Note: no visible binding for global variable 'CLOSE'

#Thay đổi màu tăng giảm một chút
candleChart(data=FPT,width=0.9,colour=c('#FFBF00','#964B00'))

Hoặc cách đơn giản nhất là sử dụng quantmod

library(quantmod)
xts_FPT <- as.xts(FPT[,c("OPEN","HIGH","LOW","CLOSE","MATCH.VOLUME")])
#Sửa tên cho xts object
colnames(xts_FPT) <- c("FPT.Open","FPT.High","FPT.Low","FPT.Close","FPT.Volume")
quantmod::candleChart(xts_FPT, multi.col = TRUE, theme = "white")
## Note: no visible binding for global variable 'params' 
## Note: no visible binding for global variable 'passed.args'