Memuat
Memuat
SEM Berbasis Kovarian (lavaan) untuk Psikologi
0 kali dilihat
Menguji jalur stigma terhadap gangguan jiwa ke literasi kesehatan mental ke niat mencari bantuan psikologis dengan SEM berbasis kovarian dan indeks kecocokan model menggunakan data sintetis untuk peragaan. SEM berbasis kovarian (CB-SEM) dengan lavaan mengestimasi model pengukuran dan struktural sekaligus serta menilai kecocokan model terhadap matriks kovarian data. Cocok untuk skripsi, tesis, atau disertasi yang menguji teori (misalnya TAM atau TPB) dengan kuesioner Likert dan sampel yang cukup besar.

Menguji jalur stigma terhadap gangguan jiwa ke literasi kesehatan mental ke niat mencari bantuan psikologis dengan SEM berbasis kovarian dan indeks kecocokan model menggunakan data sintetis untuk peragaan.
| Peran | Variabel | Satuan |
|---|---|---|
| Utama | Niat mencari bantuan psikologis | Likert 1-5 |
| Pendukung 1 | Stigma terhadap gangguan jiwa | Likert 1-5 |
| Pendukung 2 | Literasi kesehatan mental | Likert 1-5 |
Model cocok dengan data (CFI = 0.997, TLI = 0.997, RMSEA = 0.016, SRMR = 0.033). Stigma terhadap gangguan jiwa berpengaruh langsung terhadap Niat mencari bantuan psikologis (beta = 0.396, p < 0.001), dan efek tidak langsung melalui Literasi kesehatan mental sebesar 0.214 (p < 0.001). Model menjelaskan 53.4% variasi Niat mencari bantuan psikologis.
Dihitung dari data sintetis sebagai ilustrasi, bukan dari penelitian nyata.
SEM berbasis kovarian (CB-SEM) dengan lavaan mengestimasi model pengukuran dan struktural sekaligus serta menilai kecocokan model terhadap matriks kovarian data. Cocok untuk skripsi, tesis, atau disertasi yang menguji teori (misalnya TAM atau TPB) dengan kuesioner Likert dan sampel yang cukup besar.
Model dianggap cocok bila CFI dan TLI di atas 0,90 (lebih baik 0,95), RMSEA dan SRMR di bawah 0,08. Setelah itu laporkan loading terstandar, koefisien jalur terstandar beserta nilai p, R2 konstruk endogen, dan efek tidak langsung a*b untuk menyimpulkan peran mediator.
Skrip awal singkat dengan nama variabel proyek ini. Versi yang diserahkan disesuaikan dengan data Anda dan diberi komentar lengkap.
# Contoh kode R: Covariance-Based SEM (lavaan)
suppressPackageStartupMessages({
library(ggplot2)
library(patchwork)
library(lavaan)
})
set.seed(42)
# ---- Gaya grafik ----
pal <- c("#1f6feb", "#e8590c", "#2f9e44", "#ae3ec9", "#f59f00")
warna <- list(bg = "#f4f6fa", panel = "#ffffff", teks = "#1f2933", redup = "#5f6b78", grid = "#e3e8ee", bar = "#1d3557")
tata <- 1
theme_set(theme_minimal(base_size = 11) + theme(legend.position = "bottom"))
# ---- Data sintetis: 12 butir Likert 1-5 dari tiga konstruk laten ----
n <- 200
a <- runif(1, 0.4, 0.7) # jalur X1 -> X2 (mediator)
b <- runif(1, 0.3, 0.55) # jalur X2 -> Y
cp <- runif(1, 0.1, 0.35) # jalur langsung X1 -> Y
e_x1 <- rnorm(n)
e_x2 <- a * e_x1 + rnorm(n, 0, sqrt(1 - a^2))
e_y <- as.numeric(scale(cp * e_x1 + b * e_x2 + rnorm(n, 0, runif(1, 0.55, 0.75))))
# butir Likert: muatan acak 0.65-0.9, ambang diacak agar rata-rata butir sekitar 3.4-3.8
likert <- function(eta, k) {
sapply(seq_len(k), function(j) {
l <- runif(1, 0.65, 0.9)
s <- l * eta + rnorm(length(eta), 0, sqrt(1 - l^2))
findInterval(s, sort(c(-2, -1.1, -0.2, 0.9) + runif(1, -0.3, 0.2))) + 1
})
}
# butir Y ke-4 sedikit ikut dipengaruhi X1 (muatan silang kecil) agar kecocokan model realistis, tidak sempurna
d <- data.frame(likert(e_x1, 4), likert(e_x2, 4), likert(e_y, 3),
likert(as.numeric(scale(e_y + runif(1, 0.25, 0.5) * e_x1)), 1))
names(d) <- c(paste0("mental_illness_stigma", "_", 1:4), paste0("mental_health_literacy", "_", 1:4), paste0("help_seeking_intention", "_", 1:4))
write.csv(d, "data_contoh.csv", row.names = FALSE)
# ---- Spesifikasi model: pengukuran (=~), struktural (~), efek tidak langsung (:=) ----
model <- paste0(
"mental_illness_stigma =~ ", paste(names(d)[1:4], collapse = " + "), "\n",
"mental_health_literacy =~ ", paste(names(d)[5:8], collapse = " + "), "\n",
"help_seeking_intention =~ ", paste(names(d)[9:12], collapse = " + "), "\n",
"mental_health_literacy ~ a*mental_illness_stigma\n",
"help_seeking_intention ~ b*mental_health_literacy + c*mental_illness_stigma\n",
"tidak_langsung := a*b\n",
"total := c + a*b\n")
cat(model)
fit <- sem(model, data = d, estimator = "MLR") # ML robust (data Likert diperlakukan kontinu)
print(summary(fit, fit.measures = TRUE, standardized = TRUE, rsquare = TRUE))
# ---- Indeks kecocokan model (versi robust, cadangan versi biasa) ----
fm <- fitMeasures(fit, c("cfi.robust", "tli.robust", "rmsea.robust", "srmr", "cfi", "tli", "rmsea"))
pilih <- function(r, s) if (is.finite(fm[[r]])) fm[[r]] else fm[[s]]
idx <- c(CFI = pilih("cfi.robust", "cfi"), TLI = pilih("tli.robust", "tli"),
RMSEA = pilih("rmsea.robust", "rmsea"), SRMR = fm[["srmr"]])
print(round(idx, 3))
# ---- Koefisien terstandar ----
ss <- standardizedSolution(fit)
jalur <- ss[ss$op == "~", ]
ambil <- function(lhs, rhs) jalur[jalur$lhs == lhs & jalur$rhs == rhs, ]
j_a <- ambil("mental_health_literacy", "mental_illness_stigma"); j_b <- ambil("help_seeking_intention", "mental_health_literacy"); j_c <- ambil("help_seeking_intention", "mental_illness_stigma")
tl <- ss[ss$op == ":=" & ss$lhs == "tidak_langsung", ]
muat <- ss[ss$op == "=~", ]
r2 <- lavInspect(fit, "rsquare")
print(jalur[, c("lhs", "rhs", "est.std", "se", "pvalue")]); print(tl)
# ---- Grafik ----
singkat <- function(s, w = 18) { # nama konstruk pendek untuk grafik
k <- strsplit(s, " ")[[1]]
if (nchar(s) > w) k <- k[!tolower(k) %in% c("of", "to", "the", "and", "for", "in", "on", "with")]
i <- length(k)
while (nchar(paste(k, collapse = " ")) > w && i >= 1) {
if (nchar(k[i]) > 5) k[i] <- paste0(substr(k[i], 1, 4), ".")
i <- i - 1
}
substr(paste(k, collapse = " "), 1, w)
}
nm_k <- make.unique(unname(sapply(c("mental_illness_stigma", "mental_health_literacy", "help_seeking_intention"), singkat)), sep = " ")
bintang <- function(p) ifelse(p < 0.001, "***", ifelse(p < 0.01, "**", ifelse(p < 0.05, "*", " ns")))
elips <- function(x0, y0, rx = 0.74, ry = 0.3, id = 1) {
t_ <- seq(0, 2 * pi, length.out = 60)
data.frame(x = x0 + rx * cos(t_), y = y0 + ry * sin(t_), id = id)
}
pos <- data.frame(x = c(0, 1.6, 3.2), y = c(0, 1.25, 0), lab = nm_k)
de <- do.call(rbind, lapply(1:3, function(i) elips(pos$x[i], pos$y[i], id = i)))
# kotak indikator: X1 di kiri bawah, X2 di atas, Y di kanan bawah
ind <- data.frame(x = c(-0.9, -0.3, 0.3, 0.9, 0.7, 1.3, 1.9, 2.5, 2.3, 2.9, 3.5, 4.1),
y = rep(c(-0.95, 2.35, -0.95), each = 4), grup = rep(1:3, each = 4),
lab = paste0(rep(c("X1.", "M.", "Y."), each = 4), rep(1:4, 3)))
ind$xl <- pos$x[ind$grup]; ind$yl <- pos$y[ind$grup] + ifelse(ind$grup == 2, 0.3, -0.3)
st <- data.frame(x = c(0.45, 2.15, 0.78), y = c(0.3, 0.95, 0), xend = c(1.05, 2.75, 2.42), yend = c(1.0, 0.3, 0),
lab = sprintf("%.2f%s", c(j_a$est.std, j_b$est.std, j_c$est.std), bintang(c(j_a$pvalue, j_b$pvalue, j_c$pvalue))),
lx = c(0.55, 2.65, 1.6), ly = c(0.78, 0.78, -0.14))
p1 <- ggplot() +
geom_segment(data = ind, aes(xl, yl, xend = x, yend = y + ifelse(grup == 2, -0.15, 0.15)), colour = warna$redup,
linewidth = 0.4, arrow = arrow(length = unit(0.07, "inches"), type = "closed")) +
geom_tile(data = ind, aes(x, y), width = 0.5, height = 0.3, fill = warna$panel, colour = warna$redup, linewidth = 0.4) +
geom_text(data = ind, aes(x, y, label = lab), colour = warna$teks, size = 2.6) +
geom_segment(data = st, aes(x, y, xend = xend, yend = yend), colour = warna$teks, linewidth = 0.9,
arrow = arrow(length = unit(0.13, "inches"), type = "closed")) +
geom_text(data = st, aes(lx, ly, label = lab), colour = warna$teks, fontface = "bold", size = 3.3) +
geom_polygon(data = de, aes(x, y, group = id, fill = factor(id)), show.legend = FALSE) +
scale_fill_manual(values = pal[1:3]) +
geom_text(data = pos, aes(x, y, label = lab), colour = warna$panel, fontface = "bold", size = 3) +
annotate("text", x = 1.6, y = -1.38, size = 3, colour = warna$teks,
label = sprintf("Std. indirect = %.3f%s R2 = %.2f", tl$est.std, bintang(tl$pvalue), r2[["help_seeking_intention"]])) +
coord_cartesian(xlim = c(-1.25, 4.45), ylim = c(-1.5, 2.6)) +
theme_void() + theme(plot.background = element_rect(fill = warna$panel, colour = NA),
plot.title = element_text(face = "bold", colour = warna$teks, margin = margin(4, 0, 4, 6))) +
labs(title = "Standardised structural model (MLR)")
df <- data.frame(indeks = factor(names(idx), levels = names(idx)), nilai = unname(idx),
ambang = c(0.9, 0.9, 0.08, 0.08), arah = c("Higher is better", "Higher is better", "Lower is better", "Lower is better"))
p2 <- ggplot(df, aes(indeks, nilai, fill = arah)) +
geom_col(width = 0.6) +
geom_errorbar(aes(ymin = ambang, ymax = ambang), width = 0.8, linetype = "dashed", colour = warna$teks, linewidth = 0.6) +
geom_text(aes(label = sprintf("%.3f", nilai)), vjust = -0.4, colour = warna$teks, size = 3) +
facet_wrap(~arah, scales = "free") +
scale_fill_manual(values = pal[4:5], guide = "none") +
scale_y_continuous(expand = expansion(mult = c(0, 0.15))) +
labs(title = "Fit indices vs cut-offs (dashed)", x = NULL, y = "Value")
muat$konstruk <- factor(nm_k[match(muat$lhs, c("mental_illness_stigma", "mental_health_literacy", "help_seeking_intention"))], levels = nm_k)
muat$butir <- factor(ind$lab, levels = rev(ind$lab))
p3 <- ggplot(muat, aes(est.std, butir, colour = konstruk)) +
geom_vline(xintercept = 0.7, linetype = "dashed", colour = warna$redup) +
geom_segment(aes(x = 0, xend = est.std, yend = butir), linewidth = 0.9) +
geom_point(size = 2.6) +
geom_text(aes(label = sprintf("%.2f", est.std)), hjust = -0.35, size = 2.6, colour = warna$teks) +
scale_colour_manual(values = pal[1:3], name = NULL) +
scale_x_continuous(limits = c(0, 1.1), breaks = seq(0, 1, 0.25)) +
labs(title = "Standardised loadings", x = "Loading", y = NULL)
p_hasil <- if (tata == 1) p1 / (p2 | p3) + plot_layout(heights = c(1.15, 1)) else p1 | (p2 / p3)
print(p_hasil)
Berkas proyek aslinya tersedia. Bukan sekadar gambar di atas: Anda mendapat proyek R yang siap dijalankan. Berkas bisa diunduh setelah pembayaran, dan kami kirim lewat WhatsApp atau email.
ZIP: analisis.R + data_contoh.csv + BACA-DULU.txt
Pilih seberapa banyak bantuan yang Anda perlukan. Setiap paket yang lebih tinggi sudah mencakup semua item paket di bawahnya. Harga belum termasuk PPN 11%.
Paket 1
Rp 500.000
belum termasuk PPN 11%
Waktu pengerjaan: 7 hari kerja
Output: Berkas R + gambar hasil
Yang Anda terima
Paket 2 · paling dipilih
Rp 1.350.000
belum termasuk PPN 11%
Waktu pengerjaan: 13 hari kerja
Output: Kode + analisis + bahan interpretasi
Termasuk semua item Paket 1, ditambah
Paket 3
Rp 3.000.000
belum termasuk PPN 11%
Waktu pengerjaan: 18-21 hari kerja
Output: Kode + analisis + pendampingan hingga siap dipresentasikan
Termasuk semua item Paket 1 & 2, ditambah
Ya. Berkas proyek aslinya berupa ZIP berisi skrip analisis.R lengkap, data_contoh.csv, dan petunjuk BACA-DULU.txt. Berkas bisa diunduh setelah pembayaran, dan kami kirim lewat WhatsApp atau email. Untuk data Anda sendiri (Paket 2 dan 3), skrip disesuaikan dengan dataset Anda.
Cocok. SEM Berbasis Kovarian (lavaan) lazim dipakai pada jenjang ini di bidang Psikologi. Analisis kami sesuaikan dengan pertanyaan penelitian, data Anda sendiri, dan ketentuan dosen pembimbing.
Bukan. Lembar hasil dihitung dari data sintetis sebagai ilustrasi jenis keluaran R Studio. Untuk pesanan Anda, metode yang sama dijalankan pada data penelitian Anda sendiri.
Itu tujuan paketnya. Setiap skrip diberi komentar, dan Paket 3 mencakup dua sesi pendampingan serta latihan tanya jawab supaya Anda bisa menjelaskan metode dan hasilnya saat seminar dan sidang.
Tiap proyek punya tiga paket: Paket 1 (kode dan penjelasan) Rp 500.000, Paket 2 (analisis data Anda dan interpretasi) Rp 1.350.000, dan Paket 3 (pendampingan lengkap) Rp 3.000.000, belum termasuk PPN 11%. Data yang besar, metode tambahan, atau tenggat ketat menyesuaikan penawaran setelah konsultasi singkat.
Lembar hasil memakai data sintetis sebagai ilustrasi. R adalah bahasa pemrograman proyek R Foundation; RStudio dan Posit adalah merek dagang Posit PBC.
Kembali ke portofolio R Studio