1 THÔNG TIN CƠ BẢN CỦA DỮ LIỆU

1.1 Đọc dữ liệu

data <- read.csv(file.choose(), header = TRUE)

Ở dòng lệnh này, tụi em đã chọn file transactions_data.csv để thêm file csv vào RStudio. Sau đó tụi em đã gán data.frame này vào biến data để thuận lợi phân tích.

1.2 Xác định số quan sát, số biến của dữ liệu

dim(data)
## [1] 13305915       12

Từ đây cho thấy bộ dữ liệu có 13305915 dòng12 cột. Tương ứng với 13305915 quan sát12 biến

1.3 Phân loại dữ liệu

str(data)
## 'data.frame':    13305915 obs. of  12 variables:
##  $ id            : int  7475327 7475328 7475329 7475331 7475332 7475333 7475334 7475335 7475336 7475337 ...
##  $ date          : chr  "2010-01-01 00:01:00" "2010-01-01 00:02:00" "2010-01-01 00:02:00" "2010-01-01 00:05:00" ...
##  $ client_id     : int  1556 561 1129 430 848 1807 1556 1684 335 351 ...
##  $ card_id       : int  2972 4575 102 2860 3915 165 2972 2140 5131 1112 ...
##  $ amount        : chr  "$-77.00" "$14.57" "$80.00" "$200.00" ...
##  $ use_chip      : chr  "Swipe Transaction" "Swipe Transaction" "Swipe Transaction" "Swipe Transaction" ...
##  $ merchant_id   : int  59935 67570 27092 27092 13051 20519 59935 39021 50292 3864 ...
##  $ merchant_city : chr  "Beulah" "Bettendorf" "Vista" "Crown Point" ...
##  $ merchant_state: chr  "ND" "IA" "CA" "IN" ...
##  $ zip           : num  58523 52722 92084 46307 20776 ...
##  $ mcc           : int  5499 5311 4829 4829 5813 5942 5499 4784 7801 5813 ...
##  $ errors        : chr  "" "" "" "" ...

Từ câu lệnh cho thấy bộ dữ liệu có 6 biến định tính6 biến định lượng

1.4 Số quan sát bị thiếu

missing_col <- colSums(is.na(data))
missing_value <- sum(is.na(data))
print(missing_value)
## [1] 1652706
print(missing_col)
##             id           date      client_id        card_id         amount 
##              0              0              0              0              0 
##       use_chip    merchant_id  merchant_city merchant_state            zip 
##              0              0              0              0        1652706 
##            mcc         errors 
##              0              0

Ở câu lệnh này chúng em đã xác định các giá trị bị thiếu theo cộttổng giá trị bị thiếu của bộ dữ liệu. Kết quả cho thấy có 1652706 giá trị bị thiếu và các giá trị này nằm ở cột zip

1.5 Số quan sát bị trùng lặp

1.5.1 Số hàng trùng hoàn toàn

library(data.table)
setDT(data)
dup_count <- data[, .N, by = names(data)][N > 1, .N]
print(dup_count)
## [1] 0

Ở dòng lệnh này, chúng em sử dụng gói data.table phù hợp xử lý dữ liệu có số quan sát lớn (hơn 13 triệu quan sát). Kết quả thu được: không có quan sát nào bị trùng

1.5.2 Trùng theo card_id

dup_id <- length(unique(data$card_id))
print(dup_id)
## [1] 4071

Kết quả phân tích cho thấy trong tổng số hơn 13 triệu giao dịch, chỉ có 4071 thẻ khác nhau được sử dụng.

1.6 Giải thích ý nghĩa các biến

Bộ dữ liệu bao gồm thông tin chi tiết về các giao dịch thanh toán bằng thẻ trong một khoảng thời gian nhất định. Mỗi dòng trong dữ liệu đại diện cho một giao dịch duy nhất, được mô tả thông qua 12 biến chính.Cụ thể:

  • Biến id là mã định danh duy nhất cho từng giao dịch, giúp phân biệt các giao dịch với nhau.

  • Biến date ghi nhận thời điểm giao dịch xảy ra, bao gồm ngày và giờ chính xác.

  • Biến client_id (mã khách hàng) cho biết thông tin lưu trữ về khách hàng.

  • Biến card_id (mã thẻ được sử dụng), cho phép theo dõi hành vi tiêu dùng theo từng cá nhân hoặc thiết bị thanh toán.

  • Biến amount thể hiện số tiền của giao dịch, trong đó giá trị dương tương ứng với số tiền giao dịch thành cônggiá trị âm tương ứng với số tiền giao dịch thất bại(hoàn tiền).

  • Biến use_chip thể hiện phương thức thanh toán giao dịch, bao gồm ba loại: Chip Transaction (giao dịch qua chip EMV), Online Transaction (thanh toán trực tuyến),Swipe Transaction (quẹt thẻ từ).

  • Biến merchant_id thể hiện mã nhà bán hàng

  • Biến merchant_city thể hiện thành phố/ nơi thực hiện giao dịch

  • Biến merchant_state thể hiện bang/ tiểu bang của nơi thực hiện giao dịch

  • Biến zip thể hiện mã bưu điện tương ứng với từng thành phố - nơi thực hiện giao dịch

  • Biến mcc (Merchant Category Code) phân loại ngành nghề kinh doanh của nhà bán hàng

    Ví dụ:

    • Cửa hàng tạp hóa, siêu thị: mcc = 5499
    • Cửa hàng thực phẩm khác: mcc = 5541
    • Cửa hàng xăng dầu: mcc = 5812
    • Nhà hàng, quán ăn: mcc = 5812
  • Biến errors ghi nhận mã lỗi (nếu có) trong quá trình xử lý giao dịch; giá trị bằng 0 cho thấy giao dịch thành công, trong khi các lỗi chi tiết sẽ được ghi chú ở mục này phản ánh sự cố kỹ thuật hoặc từ chối thanh toán.

1.7 Xử lý dữ liệu

library(DT)
data$amount <- as.numeric(gsub("\\$", "", data$amount))
data_duong <- data[data$amount >0,]
data_am <-  data[data$amount <0,]
  • Vì kiểu dữ liệu của cột amount là dạng character (ví dụ $80.00), nên chúng em đã chuyển định dạng cột này thành kiểu numberic (ví dụ 80.00) bằng cách bỏ đi ký tự $.

  • Ngoài ra do tính chất của biến amountdương nếu có số tiền giao dịch thành côngâm nếu là số tiền giao dịch bị hoàn lại. Chính vì thế, nhóm em đã chia số tiền giao dịch này thành hai mẫu khác nhau tương ứng với đặc tính giao dịch.

2 PHÂN TỔ CÁC BIẾN

2.1 Phân tổ số giao dịch theo nơi thực hiện giao dịch

library(DT)
counts <- sort(table(data$merchant_city), decreasing = TRUE)
counts <- as.data.frame(counts)
colnames(counts) <- c("Nơi thực hiện giao dịch","Số giao dịch")
datatable(head(counts,1000))

Kết quả cho thấy số lượng giao dịch trực tuyến (online) chiếm tỷ trọng cao nhất với 1563700 giao dịch

2.1.1 Phân tổ số lần giao dịch thành công theo mã khách hàng

counts_duong <- sort(table(data_duong$client_id), decreasing = TRUE)
counts_duong <- as.data.frame(counts_duong)
colnames(counts_duong) <- c("Client_id","Số lần giao dịch thành công")
datatable(head(counts_duong,1000))

Kết quả cho thấy khách hàng có id 1963 có số lần giao dịch thành công cao nhất với 42137 giao dịch.

2.1.2 Phân tổ số lần giao dịch thất bại theo mã khách hàng

data_abs <- data_am
data_abs$amount <- abs(data_am$amount)
counts_am <- sort(table(data_abs$client_id), decreasing = TRUE)
counts_am <- as.data.frame(counts_am)
colnames(counts_am) <- c("Client_id","Số lần giao dịch bị hoàn tiền")
datatable(head(counts_am,1000))

Kết quả cho thấy khách hàng có id 1888 có số lần giao dịch thất bại và bị hoàn tiền nhiều nhất với *10957 giao dịch**.

2.2 Phân tổ số lần giao dịch thành công theo phương thức thanh toán

counts_duong1 <- sort(table(data_duong$use_chip), decreasing = TRUE)
counts_duong1 <- as.data.frame(counts_duong1)
colnames(counts_duong1) <- c("Phương thức thanh toán","Số lần giao dịch thành công")
datatable(counts_duong1)
library(ggplot2)
ggplot(counts_duong1, aes(x = reorder(`Phương thức thanh toán`, `Số lần giao dịch thành công`), 
                                y = `Số lần giao dịch thành công`)) +
  geom_col(fill = "steelblue") +
  coord_flip() +  
  labs(title = "Số lần giao dịch thành công theo các phương thức",
       x = "Phương thức thanh toán", y = "Số lần") +
  theme_minimal()+
  theme(plot.title = element_text(hjust = 0.5))

Từ kết quả này, chúng em có nhận xét sau: Số lần giao dịch thành công bằng hình thức quẹt thẻ là 6571735 giao dịch, chiếm ưu thế vượt trội hơn hai phương thức còn lại do tính tiện lợi và nhanh chóng trong cách thức giao dịch.

2.3 Phân tổ số lần giao dịch thất bại theo phương thức thanh toán

counts_am1 <- sort(table(data_abs$use_chip), decreasing = TRUE)
counts_am1 <- as.data.frame(counts_am1)
colnames(counts_am1) <- c("Phương thức thanh toán","Số lần giao dịch thất bại")
datatable(counts_am1)
 ggplot(counts_am1, aes(x = reorder(`Phương thức thanh toán`, `Số lần giao dịch thất bại`), 
                                y = `Số lần giao dịch thất bại`)) +
  geom_col(fill = "tomato") +
  coord_flip() +
  labs(title = "Số lần giao dịch thất bại theo các phương thức",
       x = "Phương thức thanh toán", y = "Số lần") +
  theme_minimal()+
  theme(plot.title = element_text(hjust = 0.5))

Từ kết quả này, chúng em có nhận xét sau: Số lần giao dịch thất bại bằng hình thức quẹt thẻ là 637314 giao dịch, vượt trội hơn phương thức còn lại là online.Ngoài ra, ta không thấy phương thức sử dụng chip trong bảng này. Giải thích cho những điều này gồm hai lý do chính sau:

  • Thứ nhất, do tính tiện lợi và nhanh chóng trong cách thức giao dịch của phương thức quẹt thẻ nên phương thức này được ưa chuộng -> Số lượng giao dịch bằng phương thức này lớn -> Khả năng thanh toán thất bại cũng nhiều hơn hai phương án còn lạ.
  • Thứ hai, phương thức sử dụng chip không được xuất hiện bởi vì tính an toàn và bảo mật của phương thức này được xem là cao nhất trong hai phương thức còn lại -> Khả năng thất bại khi giao dịch bằng phương thức này là không thể.

3 PHÂN TÍCH CÁC BIẾN

Ở phần này, chúng em lựa chọn 2 biến chính để phân tích là use_chipamount

3.1 Biến use_chips

table(data$use_chip)
## 
##   Chip Transaction Online Transaction  Swipe Transaction 
##            4780818            1557912            6967185

Kết quả cho thấy số lượng giao dịch bằng Chip là 4780818, bằng Thẻ là 6967185 và giao dịch trực tuyến là 1557912 . Điều này chứng tỏ, việc giao dịch bằng Thẻ trở nên phổ biến và được ưa chuộng vì sự tiện lợi và nhanh chóng của phương thức này vượt trội hơn so với hai phương thức còn lại.

3.2 Biến amount

Vì phương thức thanh toán có ba loại chính là Chip Transaction, Online Transaction Swipe Transaction mà mỗi loại lại có số tiền giao dịch khác nhau, nên chúng em đã lập bảng thống kê mô tả cho từng loại, nhằm mục đích để so sánh hành vi chi tiêu giữa các phương thức thanh toán, từ đó rút ra những nhận định về xu hướng sử dụng, mức độ an toàn và đặc điểm khách hàng tiềm năng.

3.2.1 Số tiền của giao dịch thành công

Thống kê mô tả

library(dplyr)
summary1<- data_duong %>%
  group_by(use_chip) %>%
  summarise(
    mean = mean(amount),
    Q1 = quantile(amount, 0.25),
    median = median(amount),
    Q3 = quantile(amount, 0.75),
    var = var(amount),
    sd = sd(amount),
    min = min(amount),
    max = max(amount)
  ) %>%
  mutate(across(where(is.numeric), ~ round(., 2)))
datatable(
  summary1, caption = "Thống kê mô tả các giao dịch thành công theo các phương thức")

Biểu đồ Box-plot

library(ggplot2)
ggplot(data_duong, aes(x = use_chip, y = amount, fill = use_chip)) +
  geom_boxplot(show.legend = FALSE) +
  coord_cartesian(ylim = c(0, 250)) + 
  labs(
    title = "Biểu đồ Box-Plot cho giá trị giao dịch thanh toán thành công theo từng phương thức",
    x = "Phương thức thanh toán",
    y = "Số tiền (USD)"
  ) +
  theme_minimal()+ 
  theme(plot.title = element_text(hjust = 0.5))

Từ bảng thống kê mô tả trên và biểu đồ Box-plot, chúng em đưa ra những nhận xét sau:

1. Về Giá trị Giao dịch Trung bình:

  • Giao dịch trực tuyến có giá trị trung bình cao nhất, ở mức $58.78. Điều này cho thấy người dùng có xu hướng chi tiêu nhiều tiền hơn cho mỗi lần mua sắm online.
  • Giá trị trung bình của giao dịch Quẹt thẻ ($49.72) và Chip ($49.07) khá tương đồng và thấp hơn so với giao dịch trực tuyến.

2. Về Giá trị trung vị:

  • Trung vị ($35.30) của giao dịch Online thấp hơn đáng kể so với trung bình ($58.78), cho thấy phân phối lệch phải. Điều này là phần lớn các giao dịch trực tuyến có giá trị nhỏ hơn $35.30, nhưng sự tồn tại của một số ít giao dịch có giá trị rất lớn đã kéo giá trị trung bình lên cao.
  • Tương tự, trung vị của giao dịch Swipe ($30.88) và Chip ($30.80) cũng thấp hơn mức trung bình của chúng, cho thấy phân phối cũng bị lệch phải. Điều này phản ánh hành vi mua sắm tại quầy, nơi đa số là các giao dịch chi tiêu hàng ngày có giá trị thấp, trong khi các giao dịch lớn ít xảy ra hơn nhưng vẫn ảnh hưởng đến giá trị trung bình chung.

3. Về Mức độ Biến động (Độ lệch chuẩn):

  • Giao dịch trực tuyến có độ lệch chuẩn cao nhất ($89.20). Điều này có nghĩa là giá trị các đơn hàng online rất đa dạng và phân tán, có thể từ những món hàng rất rẻ đến những sản phẩm cực kỳ đắt tiền.
  • Độ biến động của giao dịch Quẹt thẻ ($72.21) và Chip ($70.68) thấp hơn, cho thấy giá trị chi tiêu khi thanh toán tại quầy có phần ổn định và ít chênh lệch hơn so với online.

3.2.2 Số tiền của giao dịch thất bại/ hoàn lại

Thống kê mô tả

summary2 <- data_abs %>%
  group_by(use_chip) %>%
  summarise(
    mean = mean(amount),
    Q1 = quantile(amount, 0.25),
    median = median(amount),
    Q3 = quantile(amount, 0.75),
    var = var(amount),
    sd = sd(amount),
    min = min(amount),
    max = max(amount))%>%
  mutate(across(where(is.numeric), ~ round(., 2)))

datatable(summary2, 
          caption = "Thống kê mô tả các giao dịch hoàn tiền theo các phương thức")

Biểu đồ Box - plox

ggplot(data_abs, aes(x = use_chip, y = amount, fill = use_chip)) +
  geom_boxplot(show.legend = FALSE) +
  labs(
    title = "Biểu đồ Box-Plot cho giá trị hoàn tiền theo từng phương thức",
    x = "Phương thức thanh toán",
    y = "Số tiền hoàn (USD)"
  ) +
  theme_minimal()+ 
  theme(plot.title = element_text(hjust = 0.5))

Từ kết quả trên, nhóm em rút ra các nhận xét sau:

1. Về Giá trị Hoàn tiền Trung bình:

  • Online Transaction có giá trị hoàn tiền trung bình cao vượt trội, lên tới $297.56 cho mỗi giao dịch. Điều này cho thấy khi một giao dịch online bị hoàn trả, đó thường là những đơn hàng có giá trị rất lớn.
  • Giá trị hoàn tiền trung bình của Swipe ($101.75) và Chip ($98.15) thấp hơn nhiều và khá tương đồng với nhau.

2. Về Giá trị Hoàn tiền trung vị và tứ phân vị:

  • Với giao dịch Online, trung vị ($397) là một giá trị âm lớn hơn cả trung bình ($297.56), cho thấy phân phối lệch trái. Ý nghĩa kinh tế là hơn một nửa số giao dịch hoàn tiền trực tuyến có giá trị rất cao (lớn hơn $397). Điều này cho thấy việc hoàn trả các mặt hàng đắt tiền là phổ biến trong mua sắm online, chứ không chỉ là trường hợp cá biệt.
  • Ngược lại, trung vị của giao dịch Swipe ($78) và Chip ($78) là giá trị âm nhỏ hơn mức trung bình của chúng, cho thấy phân phối lệch phải. Nghĩa là 50% số lần hoàn tiền tại quầy có giá trị từ $78 trở xuống. Điều này phản ánh rằng việc hoàn trả các mặt hàng thông thường, giá trị thấp là chủ yếu, trong khi các khoản hoàn tiền lớn hơn ít xảy ra nhưng đủ để kéo giá trị trung bình lên.