Analisis eksperimen yang kredibel dimulai jauh sebelum baris kode pertama: kita harus tahu pertanyaan apa yang diajukan, uji apa yang dipakai, dan ambang keputusan yang dipakai — semuanya ditetapkan sebelum satu pun angka dilihat. Pada bagian ini kita menyusun rencana analisis lengkap untuk eksperimen waktu produksi tiga metode, lalu membangun data sintetis deterministik yang menjadi objek analisisnya.
Yang kita tetapkan pada bagian ini:
- konteks eksperimen: tiga metode produksi dan hipotesis yang diuji,
- variabel dan replikat: apa yang diukur, berapa kali, dan mengapa,
- rencana analisis yang dikunci di awal beserta diagram alurnya,
- data sintetis deterministik lewat fungsi
buatDataEksperimen.
Konteks Eksperimen #
Tim produksi sebuah pabrik kemasan menguji tiga cara menjalankan batch yang sama. Setiap batch memakai operator, mesin, dan bahan yang sama; satu-satunya hal yang berbeda adalah prosedurnya:
| Metode | Prosedur | Waktu dasar |
|---|---|---|
| A | prosedur standar manual | 50 menit |
| B | prosedur standar + checklist pra-produksi | 45 menit |
| C | prosedur standar + mesin bantu semi-otomatis | 52 menit |
Pertanyaan praktisnya: apakah ketiga metode menghasilkan waktu produksi rata-rata yang berbeda, atau selisih yang terlihat cuma kebetulan sampling? Pertanyaan itu diterjemahkan menjadi hipotesis statistik:
- H0: mean waktu ketiga metode sama — muA = muB = muC.
- H1: minimal satu pasangan metode berbeda mean-nya.
- Alpha: 0.05 — peluang kesalahan tipe I yang kita tanggung.
Perhatikan bahwa H1 tidak menyebut metode mana yang tercepat. ANOVA pada Bagian 3 hanya menjawab “ada perbedaan atau tidak”; menentukan pasangan mana yang berbeda adalah tugas uji posthoc, bukan tebakan awal.
Variabel dan Replikat #
Desain eksperimen ini memetakan peran tiap besaran secara eksplisit:
| Peran | Variabel | Skala |
|---|---|---|
| Independen (perlakuan) | metode produksi | kategorik, 3 level (A/B/C) |
| Dependen (hasil) | waktu produksi per batch | kontinu, menit |
| Kontrol | operator, mesin, bahan, urutan batch | dijaga sama |
| Replikat | 10 batch per metode | total 30 pengamatan |
Mengapa 10 replikat, bukan 3 atau 100? Dengan 10 per metode, derajat bebas dalam-grup ANOVA mencapai N - k = 27 dan setiap uji t berpasangan memperoleh df = 18 — cukup untuk mendeteksi efek seukuran desain ini. Lebih banyak replikat tentu lebih kuat, tetapi setiap batch memakan waktu mesin dan operator; 10 adalah kompromi praktis yang lazim di eksperimen industri kecil. Ukuran sampel yang pas untuk efek yang diharapkan seharusnya dihitung lewat power analysis — kita bahas sebagai ide pengembangan di Bagian 4.
Desain kita juga seimbang: semua metode mendapat jumlah replikat yang sama. Keseimbangan membuat rumus ANOVA dan uji t sederhana tetap berlaku tanpa pembobotan khusus.
Rencana Analisis: Dikunci Sebelum Data Dilihat #
Urutan uji ditetapkan sekarang, dan dijalankan apa adanya nanti: statistik deskriptif dulu untuk melihat bentuk data, uji ringan normalitas, baru ANOVA, lalu posthoc hanya jika ANOVA signifikan:
Diagram itu bukan formalitas. Setiap cabang keputusan sudah tercatat sebelum data ada, sehingga tidak ada ruang untuk mengganti uji di tengah jalan demi hasil yang “lebih signifikan”.
Data Sintetis Deterministik #
Kita tidak punya lini produksi sungguhan, jadi eksperimennya disimulasikan: data dibangun dari parameter desain berikut:
| Metode | Mean target | Sebaran target (std) | Replikat |
|---|---|---|---|
| A | 50 menit | sekitar 2 | 10 |
| B | 45 menit | sekitar 2 | 10 |
| C | 52 menit | sekitar 3 | 10 |
Setiap nilai dihitung dari formula tetap: waktu = dasar + offset, dengan offset 10 angka tetap per metode yang berjumlah nol — jadi mean sampel tepat sama dengan waktu dasar. Tanpa rand sama sekali, mean, uji F, p-value, dan isi laporan identik di setiap eksekusi dan di kedua mesin. Determinisme memudahkan pelajaran (angka di halaman ini bisa direproduksi persis) sekaligus membuat uji otomatis di Bagian 4 bermakna.
Menulis buatDataEksperimen.m #
Fungsi berikut membangun data, mengemasnya sebagai struct, dan menyimpan CSV format panjang. Simpan sebagai src/buatDataEksperimen.m:
function data = buatDataEksperimen()
% BUATDATAEKSPERIMEN Data eksperimen sintetis yang deterministik.
% data = buatDataEksperimen() menghasilkan data waktu produksi tiga
% metode (A, B, C) x 10 replikat, lalu menyimpannya sebagai
% data_eksperimen.csv di folder kerja aktif.
%
% Data sengaja dibangun dari angka tetap, bukan rand: nilai = waktu
% dasar metode + offset tetap per replikat. Offset tiap metode
% berjumlah nol sehingga mean sampelnya tepat sama dengan waktu
% dasar. Dengan begitu seluruh analisis dan uji otomatis menghasilkan
% angka yang sama setiap kali dijalankan, di MATLAB maupun Octave.
%
% Struct keluaran memiliki field:
% .label - label metode {'A' 'B' 'C'}
% .waktu - matriks 3x10; baris k = 10 replikat metode ke-k
% .n - jumlah replikat per metode
% .file - nama berkas CSV yang ditulis
label = {'A', 'B', 'C'};
dasar = [50, 45, 52]; % waktu dasar tiap metode (menit): A, B, C
% Offset tetap per replikat (10 angka tetap, BUKAN hasil rand).
% Desain sebaran: A sekitar 50 +/- 2, B sekitar 45 +/- 2,
% C sekitar 52 +/- 3.
offsetA = [ -2.2 2.4 -0.7 2.9 -2.7 0.9 -1.5 1.6 -0.4 -0.3 ];
offsetB = [ -2.4 1.8 -1.2 2.6 -1.9 0.7 2.2 -0.9 1.4 -2.3 ];
offsetC = [ -2.9 4.1 -1.4 3.2 -3.5 0.4 2.7 -0.8 1.6 -3.4 ];
n = 10;
waktu = [dasar(1) + offsetA;
dasar(2) + offsetB;
dasar(3) + offsetC];
data.label = label;
data.waktu = waktu;
data.n = n;
data.file = 'data_eksperimen.csv';
% Simpan CSV format panjang: kolom 1 = kode metode (1..3),
% kolom 2 = waktu (menit). Baris diurut per metode: A lalu B lalu C.
% Transpose dulu supaya urutan kolom-major(:) mengikuti urutan metode.
kode = repelem((1:numel(label))', n);
waktuKolom = waktu'; % 10x3: kolom k = replikat metode ke-k
M = [kode, waktuKolom(:)]; % kode dan waktu sebaris
% Baris header ditulis lewat fopen/fprintf agar identik di semua mesin.
fid = fopen(data.file, 'w');
if fid < 0
error('buatDataEksperimen:gagal', ...
'Tidak bisa menulis berkas %s.', data.file);
end
fprintf(fid, 'metode,waktu\n');
fclose(fid);
% Data numerik: pakai writematrix bila tersedia (MATLAB R2019a+),
% jika tidak jatuh ke dlmwrite (Octave / MATLAB lama).
if exist('writematrix', 'file') || exist('writematrix', 'builtin')
writematrix(M, data.file, 'WriteMode', 'append');
else
% '%g' menjaga kode metode tampil sebagai 1, bukan 1.0
dlmwrite(data.file, M, '-append', 'delimiter', ',', 'precision', '%g');
end
endMari kita bedah baris-baris kode di atas:
- Baris 25-27 (
offsetAsampaioffsetC): sepuluh offset tetap per metode. Jumlahkan nilainya: semuanya nol — karena mean = dasar + mean(offset), mean sampel tiap metode jatuh tepat pada 50, 45, dan 52. Sebaran offset dipilih agar std sampel mendekati 2, 2, dan 3 menit. - Baris 30-32 (
waktu = [dasar(1) + offsetA; ...]): formula tetap yang dijanjikan — satu baris per metode, tanparand. Matrikswaktuberukuran 3x10: baris = metode, kolom = replikat. - Baris 34-37 (
data.label = label; ...): struct keluaran membawa label, data mentah, jumlah replikat, dan nama berkas. Fungsi-fungsi analisis di bagian berikutnya cukup menerima struct ini sebagai masukan tunggal. - Baris 42 (
kode = repelem((1:numel(label))', n);): kode metode numerik 1-3, masing-masing diulang 10 kali. Format panjang (satu baris per pengamatan) adalah bentuk standar data eksperimen di dunia nyata. - Baris 43-44 (
waktuKolom = waktu'; M = [kode, waktuKolom(:)];): transpose + operator(:)mengurutkan nilai kolom-per-kolom sehingga A dulu, lalu B, lalu C — persis mengikuti urutankode. Tanpa transpose,waktu(:)akan berpindah baris-per-baris (A1, B1, C1, A2, …) dan kode metode salah sebaris dengan nilainya. - Baris 47-53 (
fid = fopen(...)sampaifclose(fid);): baris headermetode,waktuditulis lewatfopen/fprintfyang identik di semua mesin, lalu berkas ditutup supaya mode append berikutnya mulai dari baris baru. - Baris 57-62 (
if exist('writematrix', ...) ... end): guard kompatibilitas.writematrix(MATLAB R2019a+) menulis data denganWriteModeappend; Octave tidak memilikinya (existmengembalikan 0), jadi eksekusi jatuh kedlmwriteklasik dengan opsi-append. Presisi'%g'menjaga kolom kode tampil1, bukan1.0.
Menjalankan fungsi tersebut dari folder kerja menghasilkan struct dan berkas CSV:
% driver: bangun data lalu periksa hasilnya
data = buatDataEksperimen();
fprintf('%d metode x %d replikat -> %s\n', numel(data.label), data.n, data.file);
fprintf('mean per metode: %s\n', mat2str(mean(data.waktu, 2)));Output yang Dihasilkan:
3 metode x 10 replikat -> data_eksperimen.csv
mean per metode: [50;45;52]Mean tiap metode jatuh persis pada waktu dasar — konsekuensi offset yang berjumlah nol. Isi data_eksperimen.csv yang tertulis di folder kerja:
metode,waktu
1,47.8
1,52.4
1,49.3
1,52.9
1,47.3
1,50.9
1,48.5
1,51.6
1,49.6
1,49.7
2,42.6
2,46.8
2,43.8
2,47.6
2,43.1
2,45.7
2,47.2
2,44.1
2,46.4
2,42.7
3,49.1
3,56.1
3,50.6
3,55.2
3,48.5
3,52.4
3,54.7
3,51.2
3,53.6
3,48.6Kolom metode memakai kode numerik 1-3; label 'A', 'B', 'C' hidup di data.label sebagai lapisan tampilan. Pemisahan ini lazim: berkas data menyimpan angka, pemetaan ke nama disimpan terpisah.
Rencana terkunci dan data siap. Bagian 2 mulai merangkum data itu: mean, std, median, standard error, confidence interval, dan box plot pembanding untuk tiap metode.