Pemodelan dan Teori Risiko

Ujian Tengah Semester


Kontak : \(\downarrow\)
Email
Instagram https://www.instagram.com/arifin.alicia/
RPubs https://rpubs.com/aliciaarifin/
Nama Alicia Arifin
NIM 20214920001
Prodi Statistika

Note

replace the * sign with the last two digits of your Student ID number.
replace the # sign with the last one digit of your Student ID number.

Nomor 1

Consider a portfolio consisting of five stocks from different sectors in Indonesia and analyze the diversification benefits of combining stocks. Your answer should cover at least the following steps:

a.

Use quantmod for downloading stock data.

library(quantmod)
library(PerformanceAnalytics)

kode_saham <- c("BBCA.JK","ANTM.JK","ASII.JK","KAEF.JK","INDF.JK")
nama_saham <- c("Bank Central Asia", "Aneka Tambang", "Astra Internasional", "Kimia Farma", "Indofood Sukses Makmur")

getSymbols(kode_saham, from ="2023-03-01", to="2024-03-01", src="yahoo", adjust=F)
## [1] "BBCA.JK" "ANTM.JK" "ASII.JK" "KAEF.JK" "INDF.JK"
prices <- NULL
for (stock in kode_saham){
  prices<- cbind(prices, Cl(get(stock)))
}

b & c

Define a function calculate_returns() to calculate daily returns from the closing prices of the stocks and apply this function to each stock’s price series
Combine the returns of all stocks into a single data frame.

return <- data.frame(Return.calculate(prices))
tail(return)
prices<- as.data.frame(prices)

n =count(prices) # tentukan berpa banyak kolom
baris <- c(2 : (n$n)-1)
colnames(prices) <- c(kode_saham)
# membuat function return.
calculate_return <- function(kode, from.d, until.d, data){
  kolom = which(kode_saham==kode)
  n=count(data)
  baris = c(2:n$n)
  date_prices = seq.Date(from =as.Date(from.d), to =as.Date(until.d), "day")
  f.r = which(date_prices == from.d)
  l.r = which(date_prices == until.d)
  baru = data[c(f.r:l.r),kolom]
  return = data.frame(
    "Tanggal" = date_prices,
    kode = baru,
    "Return" = NA
  )
  for (i in baris){
  return$Return[i] = (return$Return[i-1] -return$Return[i]) /return$Return[i-1]
  }
  paste(return)
}


# calculate_return("BBCA.JK", "2024-01-01", "2024-03-01", prices)

d.

Calculate the correlation matrix of returns using cor().

cor.matrix <- cor(na.omit(return))
mask <- matrix(FALSE, nrow = nrow(cor.matrix), ncol=ncol(cor.matrix))
mask[lower.tri(mask)] <-TRUE
colnames(cor.matrix) <- rownames(cor.matrix) <- nama_saham
cor.matrix
##                        Bank Central Asia Aneka Tambang Astra Internasional
## Bank Central Asia             1.00000000    0.14008648        0.2071931151
## Aneka Tambang                 0.14008648    1.00000000        0.1677670025
## Astra Internasional           0.20719312    0.16776700        1.0000000000
## Kimia Farma                   0.01443835    0.10759067       -0.0000206354
## Indofood Sukses Makmur        0.08016220    0.07793943        0.0898089530
##                          Kimia Farma Indofood Sukses Makmur
## Bank Central Asia       0.0144383476            0.080162200
## Aneka Tambang           0.1075906749            0.077939430
## Astra Internasional    -0.0000206354            0.089808953
## Kimia Farma             1.0000000000           -0.005582388
## Indofood Sukses Makmur -0.0055823882            1.000000000

e.

Visualize the correlation matrix using corrplot().

library(corrplot)
corrplot(cor.matrix, method = "number")

dilihat dari korelasi antar variabel, dilihat bahwa korelasinya kurang dari 0,5 atau emmiliki korelasi lemah antar variabel. Hal ini mengatakan bahwa antar saham saling Independen atau memiliki pola sendiri.

f.

Calculate the portfolio’s returns and standard deviation based on equal weights for each stock.

banyak_data <- length(return)
bobot <- rep(1/banyak_data, banyak_data)


portofolio_return <-rowSums(na.omit(return*bobot ))
mean(portofolio_return) # return portofolio
## [1] -0.0003499437
sd <- sqrt(var(portofolio_return));sd # standar deviasi Portofolio
## [1] 0.01068099

Portofolio memiliki return sebanyak -0,0003499% dan standar deviasi sebanyak 0,016%. Dilihat dari return dan standar deviasi yang sangat kecil, bisa dibilang saham nya lumayan stabil, tetapi returnnya minus. walaupun -0,0003499% terbilang kecil. Saham pada portofolio ini mempertahankan nilai valuenya selama setahun. standar deviasi yang sangat kecil juga bisa dibilang retunnya stabil selama setahun belakangan ini.

g.

Calculate the diversification ratio, which measures the extent to which the portfolio’s risk is reduced due to diversification.

return <- na.omit(return)
rata_kolom <-apply(return,2,mean, na.rm=T)
rata_sd <- apply(return,2,sd,na.rm=T) ;rata_sd
## BBCA.JK.Close ANTM.JK.Close ASII.JK.Close KAEF.JK.Close INDF.JK.Close 
##    0.01012990    0.01720068    0.01458971    0.04098078    0.01139047
diversification_ratio <- function(sd, sd_kolom) {
  weighted_avg_individual_sd <- sum(sd_kolom) / length(sd_kolom)
  diversification_ratio <- weighted_avg_individual_sd / sd
  return(diversification_ratio)
}

diversification_ratio(sd,rata_sd)
## [1] 1.765595

h.

Define the objective function and constraints for portfolio optimization. Here, we aim to maximize the portfolio return subject to the constraint that the sum of portfolio weights equals 1.

library(quadprog)
library(Matrix)
expected_return <- c(0.05, 0.05,0.05,0.05,0.05)
covariance_matrix <- matrix(cor.matrix, nrow=5)

pd_D_mat <- nearPD(covariance_matrix)
D_mat <- as.matrix(pd_D_mat$mat)
d_vec <- rep(0, length(expected_return))
A_mat <- cbind(rep(1, length(expected_return)), diag(length(expected_return)))
b_vec <- c(1, d_vec)

output <- solve.QP(Dmat = D_mat, dvec = d_vec, Amat = A_mat, bvec = b_vec, meq = 1)

# Optimal portfolio weights
optimal_weights <- output$solution
optimal_weights
## [1] 0.1839250 0.1660304 0.1799076 0.2466669 0.2234701

i & j.

Find the optimal portfolio weights that maximize the portfolio return given the covariance matrix and constraints. Visualize the optimal weights assigned to each stock in the portfolio.

library(dplyr)

optimal <- data.frame(
  Saham = nama_saham,
  Weight = optimal_weights
)
optimal <- optimal %>% 
  arrange(desc(Saham)) %>%
  mutate(prop =round(Weight / sum(optimal$Weight)*100,3)) %>%
  mutate(ypos = cumsum(prop)- 0.5*prop )

optimal
library(ggplot2)
ggplot(optimal, aes(x="", y=prop, fill=Saham)) +
  geom_bar(stat="identity", width=1, color="white") +
  coord_polar("y", start=0) +
  theme_void() + 
  theme(legend.position="none") +
  geom_text(aes(x=1,y = ypos, label = Saham), color = "white", size=3) +
  scale_fill_brewer(palette="Set1")+
  ggtitle("Optimization Portofolio")

Pada grafik, disarankan membeli saham kimia farma sebanyak 24,67%, Indofood Sukses Makmur 22,37%, Bank BCA 18,4%, Astra Internasional 17,99% dan Aneka Tambang sebesar 16,6%.

k.

Calculate the expected return and volatility of the optimized portfolio using the optimal weights and covariance matrix.

# expected return
sum(expected_return * optimal_weights)
## [1] 0.05
# colatilitasnya
volatilitas <- sqrt(t(optimal_weights)%*%
  covariance_matrix%*%
  optimal_weights)
volatilitas
##           [,1]
## [1,] 0.5156884

Expected retunnya mirip dengan expected return yang kita cari (5%). Volatilitasnya sebesar 0,5%. yang berarti datanya lumayan bervolalitas karena nilai volalitilitasnya lebih dari expected return.

Nomor 2

Assume you are working as an Actuary at an Insurance Company. Your job is to define insurance claims data and analyze the risk associated with different scenarios. Consider explaining your answer in details as the following instructions:

a b c & d


Generate insurance claims data for a hypothetical insurance company with 10000 policies over 1# years.
Generate random policy premiums from a normal distribution with a mean of 10* and a standard deviation of 20.
Simulate claim frequencies for each policy from a Poisson distribution with a mean of 0.1 (i.e., on average, each policy has 0.1 claims per year).
Simulate claim amounts for each policy and each year from a normal distribution with a mean of 50
and a standard deviation of 20*.

set.seed(3)
polis = round(runif(10000, min=1, max=24700))
tahun = round(runif(10000, min=1, max=11))
harga_premi = abs(rnorm(10000, mean= 1001, sd=2001))
lamda = 0.1 # asumsi distribusi poisson

banyak_klaim <- rpois(10000, lambda = lamda)
klaim <- ifelse(banyak_klaim>0, rnorm(10000, mean = 5001, sd=2001),0)

data_asuransi = data.frame(
  "polis" = polis
)
data_asuransi$tahun = tahun
data_asuransi$harga_premi = harga_premi
data_asuransi$banyak_klaim = banyak_klaim
data_asuransi$klaim = klaim
tail(data_asuransi)

e.

Calculate total claim amounts per policy and then calculate loss ratios (total claims divided by premiums) to assess the risk associated with each policy.

library(DT)
library(random)
library(dplyr)
data_asuransi%>%
  group_by(polis)%>%
  mutate(klaim = sum(banyak_klaim))
data_asuransi$loss_ratios = data_asuransi$banyak_klaim/data_asuransi$harga_premi
head(data_asuransi$loss_ratios)
## [1] 0 0 0 0 0 0
datatable(data_asuransi)

f.

Plot a histogram of the loss ratios to visualize the distribution of risk.

hist(data_asuransi$loss_ratios)

boxplot(data_asuransi$loss_ratios)

pada histogram dilihat bahwa rationya lebih banyak yang 0 yang berarti banyak yang tidak claim. dan pada boxplot dilihat lumayan banyak pencilan, yang berarti perusahaan mengalami kerugian yang lumayan banyak.

g.

Calculate summary statistics including the mean, median, and 95th percentile of the loss ratios.

cat("mean loss ratio :", mean(data_asuransi$loss_ratios), "\n")
## mean loss ratio : 0.0006648174
cat("median loss ratio :", median(data_asuransi$loss_ratios), "\n")
## median loss ratio : 0
cat("persentil ke 95% loss ratio :", quantile(data_asuransi$loss_ratios, probs = 0.95), "\n")
## persentil ke 95% loss ratio : 0.0006945296