ITESA MUHAMMADIYAH
GANJIL 2025
Selamat Datang di R!
Sama seperti kita biasanya bekerja terorganisir dalam folder di komputer, di RStudio kita dapat melakukan hal yang sama untuk bekerja secara efisien dengan membuat proyek.
Sebuah proyek akan menjadi sebuah “folder” di dalam RStudio, sehingga direktori root kita secara otomatis akan menjadi folder proyek itu sendiri (memungkinkan kita berpindah dari satu proyek ke proyek lain menggunakan menu di kanan atas).
Kita dapat membuatnya di folder baru atau di folder yang sudah ada.

Cara yang lebih intuitif untuk bekerja dengan teks adalah menggunakan paket glue: hal pertama yang harus dilakukan adalah “membeli bukunya” (jika kita belum pernah melakukannya sebelumnya). Setelah itu muat paketnya
Dengan fungsi glue() dari paket tersebut kita dapat menggunakan variabel di dalam string. Misalnya, “umur adalah … tahun”, di mana umur disimpan dalam sebuah variabel.
Tipe fundamental lainnya adalah variabel logika atau biner (dua nilai):
TRUE: benar disimpan secara internal sebagai 1.
FALSE: salah disimpan secara internal sebagai 0.
Seperti yang akan kita lihat sebentar lagi, variabel logika sebenarnya dapat mengambil nilai ketiga: NA atau data yang hilang, yang mewakili tidak tersedia, dan akan sangat umum ditemukan dalam database.
Nilai logika biasanya merupakan hasil dari mengevaluasi kondisi logika. Misalnya, bayangkan kita ingin memeriksa apakah seseorang bernama Javi.
Dengan operator logika == kita menanyakan apakah yang kita simpan di kiri sama dengan yang ada di kanan: kita BERTANYA
Perhatikan bahwa…
Tidak sama antara <- (penugasan) dengan == (kita sedang bertanya, ini adalah perbandingan logika).
Selain perbandingan “sama dengan” versus “berbeda”, juga terdapat perbandingan urutan seperti kurang dari <, lebih dari >, <= atau >=. Apakah orang tersebut berumur kurang dari 32 tahun?
Tipe data yang sangat khusus: data bertipe tanggal.
Terlihat seperti string teks biasa tetapi seharusnya merepresentasikan suatu titik waktu. Apa yang terjadi jika kita menambahkan 1 ke sebuah tanggal?
Tanggal tidak boleh berupa string/teks: kita harus mengonversi string teks menjadi tanggal.
Untuk bekerja dengan tanggal kita akan menggunakan paket lubridate, yang harus diinstal sebelum dapat digunakan.
Setelah terinstal, dari semua paket (buku) yang kita miliki, kita akan menginstruksikan untuk memuat paket ini secara spesifik.
Attaching package: 'lubridate'
The following objects are masked from 'package:base':
date, intersect, setdiff, union
Untuk mengonversi ke tipe tanggal kita akan menggunakan fungsi as_date() dari paket lubridate (format default yyyy-mm-dd).
Dalam as_date() format tanggal default adalah yyyy-mm-dd, jadi jika string tidak dimasukkan dengan benar…
Untuk format lain kita harus menentukannya dalam argumen opsional format = ... di mana %d mewakili hari, %m bulan, %Y dalam format 4-digit tahun dan %y dalam format 2-digit tahun.
Dalam paket ini kita memiliki fungsi-fungsi yang sangat berguna untuk manajemen tanggal:
today() kita dapat langsung memperoleh tanggal saat ini.Coba kerjakan latihan-latihan berikut tanpa melihat solusinya
📝 Definisikan sebuah variabel yang menyimpan umurmu (disebut age) dan satu lagi dengan namamu (disebut name).
📝 Periksa dengan variabel age apakah nilainya BUKAN 60 tahun atau apakah namanya "Ornitorrinco" (hasilnya harus berupa variabel logika).
📝 Mengapa kode di bawah ini menghasilkan error?
📝 Definisikan variabel lain bernama siblings yang menjawab pertanyaan “apakah kamu punya saudara?” dan variabel lain yang menyimpan tanggal lahirmu (disebut birth_date).
📝 Definisikan variabel lain dengan nama belakangmu (disebut surname) dan gunakan glue() untuk memiliki, dalam satu variabel bernama full_name, nama depan dan belakangmu yang dipisahkan koma.
Saat bekerja dengan data, kita sering memiliki kolom yang merepresentasikan variabel: kita akan menyebutnya sebagai vektor, yaitu sebuah gabungan dari sel-sel (nilai) bertipe sama (mirip kolom dalam tabel).
Cara paling sederhana untuk membuat vektor adalah dengan fungsi c() (c singkatan dari concatenate), dan kamu cukup memasukkan elemen di dalam tanda kurung, dipisahkan dengan koma.
Tip
Sebuah angka tunggal x <- 1 (atau x <- c(1)) sebenarnya adalah vektor dengan panjang satu –> semua yang kita tahu cara melakukan dengan angka, dapat kita lakukan dengan vektor angka.
Jenis vektor yang paling umum adalah numerik, khususnya urutan numerik yang terkenal (misalnya, hari-hari dalam sebulan), digunakan antara lain untuk mengindeks loop.
Fungsi seq(start, end) memungkinkan kita membuat urutan numerik dari elemen awal hingga akhir, maju satu per satu.
Sebuah pintasan adalah perintah 1:n, yang mengembalikan hasil yang sama dengan seq(1, n).
Jika elemen awal lebih besar dari elemen akhir, R memahami bahwa urutannya adalah menurun.
Terkadang kita mungkin ingin mendefinisikan urutan dengan panjang tertentu.
[1] 1.000000 9.166667 17.333333 25.500000 33.666667 41.833333
[7] 50.000000
Kita mungkin juga ingin membuat vektor dengan n elemen yang diulang.
Vektor adalah gabungan elemen bertipe sama, namun tidak harus selalu berupa angka. Mari buat sebuah kalimat contoh.
Pada kasus sebelumnya, itu bukan vektor, melainkan elemen teks tunggal. Untuk membuat vektor, kita perlu menggunakan c() lagi dan memisahkan elemen dengan koma.
Apa yang akan terjadi jika kita menggabungkan elemen dari tipe yang berbeda?
Perhatikan bahwa karena semua elemen harus bertipe sama, yang dilakukan R adalah mengonversi segalanya ke teks, melanggar integritas data.
Dengan vektor numerik, kita dapat melakukan operasi aritmatika yang sama seperti dengan angka → sebuah angka adalah vektor (dengan panjang satu).
Apa yang akan terjadi jika kita menambahkan atau mengurangi nilai pada vektor?
Vektor juga dapat berinteraksi satu sama lain, sehingga kita dapat mendefinisikan, misalnya, penjumlahan vektor (elemen per elemen).
Karena operasi (misalnya penjumlahan) dilakukan elemen per elemen, apa yang terjadi jika kita menjumlahkan dua vektor dengan panjang berbeda?
Warning in x + z: longer object length is not a multiple of shorter
object length
[1] 3 7 11 9
Yang dilakukannya adalah mendaur ulang elemen: jika kita memiliki vektor dengan 4 elemen dan menambahkan vektor lain dengan 3 elemen, elemen dari vektor yang lebih pendek akan didaur ulang.
Operasi yang sangat umum adalah mengajukan pertanyaan pada data menggunakan kondisi logika. Misalnya, jika kita mendefinisikan vektor suhu…
Hari mana yang suhunya di bawah 22 derajat?
Ini akan mengembalikan sebuah vektor logika, tergantung apakah setiap elemen memenuhi kondisi yang diberikan (dengan panjang yang sama dengan vektor yang dikueri).
Kondisi logika dapat digabungkan dalam dua cara:
&) untuk mengembalikan TRUE.|).Operasi umum lainnya adalah mengakses atau mengambil elemen. Cara paling sederhana adalah menggunakan operator [i] (mengakses elemen ke-i).
Karena sebuah angka hanyalah vektor dengan panjang satu, operasi ini juga dapat diterapkan menggunakan vektor indeks untuk dipilih.
Tip
Untuk mengakses elemen terakhir tanpa khawatir tentang posisinya, kamu dapat menggunakan panjang vektor sebagai indeks x[length(x)].
Terkadang, alih-alih memilih, kita mungkin ingin menghapus elemen. Ini dilakukan dengan operasi yang sama tetapi menggunakan pengindeksan negatif: operator [-i] «membatalkan pilihan» elemen ke-i
[1] "hi" "how" "are" "you" "?"
[1] "hi" "are" "you" "?"
Dalam banyak kasus, kita ingin memilih atau menghapus elemen berdasarkan kondisi logika, tergantung nilainya, sehingga kita akan meneruskan kondisi itu sendiri sebagai indeks (ingat, x < 2 mengembalikan vektor logika).
Kita juga dapat menggunakan operasi statistik, seperti sum(), yang, diberikan sebuah vektor, mengembalikan jumlah semua elemennya.
Apa yang terjadi ketika data hilang?
Seperti yang telah disebutkan, nilai logika disimpan secara internal sebagai 0 dan 1, sehingga kita dapat menggunakannya dalam operasi aritmatika.
Misalnya, jika kita ingin mengetahui jumlah elemen yang memenuhi kondisi (misalnya, kurang dari 3), yang memenuhi akan diberi nilai 1 (TRUE), dan yang tidak akan diberi 0 (FALSE). Oleh karena itu, menjumlahkan vektor logika akan memberi kita jumlah elemen yang memenuhi kondisi.
Operasi umum lain yang berguna adalah jumlah kumulatif dengan cumsum(), yang, diberikan sebuah vektor, mengembalikan vektor di mana setiap elemen adalah jumlah dari elemen pertama, pertama ditambah kedua, pertama ditambah kedua ditambah ketiga, dan seterusnya.
Apa yang terjadi ketika data hilang?
Dalam kasus jumlah kumulatif, yang terjadi adalah dari titik itu ke depan, semua nilai kumulatif berikutnya akan menjadi hilang.
Operasi umum lain yang berguna adalah perbedaan (dengan jeda) dengan diff() yang, diberikan sebuah vektor, mengembalikan vektor dengan elemen kedua dikurangi pertama, ketiga dikurangi kedua, keempat dikurangi ketiga…dan seterusnya.
Operasi umum lainnya adalah rata-rata, median, persentil, dll.
Operasi umum lainnya adalah rata-rata, median, persentil, dll.
Terakhir, tindakan umum adalah mengetahui cara mengurutkan nilai:
sort(): mengembalikan vektor yang sudah diurutkan. Secara default dari terkecil ke terbesar tetapi dengan decreasing = TRUE bisa diubah.[1] 7 20 23 25 33 41 65 77 81
[1] 81 77 65 41 33 25 23 20 7
order(): mengembalikan vektor indeks yang harus kita gunakan untuk mengurutkan vektorCoba kerjakan latihan-latihan berikut tanpa melihat solusinya
📝 Definisikan vektor x sebagai gabungan 5 bilangan ganjil pertama. Hitung panjang vektor tersebut.
📝 Akses elemen ketiga dari x. Akses elemen terakhir (terlepas dari panjangnya, kode yang selalu bisa dijalankan). Hapus elemen pertama.
📝 Dapatkan elemen x yang lebih besar dari 4. Hitung vektor 1/x dan simpan dalam variabel.
📝 Buat vektor yang merepresentasikan nama 5 orang, salah satunya tidak diketahui.
📝 Dari vektor x latihan di atas, temukan elemen yang lebih besar dari 1 dan lebih kecil dari 7 (ketat). Temukan cara untuk mengetahui apakah semua elemen positif atau tidak.
📝 Diberikan vektor x <- c(1, -5, 8, NA, 10, -3, 9), mengapa rata-ratanya mengembalikan bukan angka tetapi seperti yang ditunjukkan kode di bawah?
📝 Diberikan vektor x <- c(1, -5, 8, NA, 10, -3, 9), ekstrak elemen yang menempati lokasi 1, 2, 5, 6.
📝 Diberikan vektor x dari latihan sebelumnya, mana yang memiliki data hilang? Petunjuk: fungsi is.sesuatu() memeriksa apakah elemen bertipe sesuatu (tekan tab).
📝 Definisikan vektor x sebagai gabungan 4 bilangan genap pertama. Hitung jumlah elemen x yang kurang dari 5 (ketat).
📝 Hitung vektor 1/x dan dapatkan versi terurut (dari terkecil ke terbesar) dalam dua cara yang memungkinkan.
Meskipun kita tidak dapat melakukan operasi aritmatika dengan mereka, beberapa operasi yang dapat kita lakukan dengan string teks akan penting.
Untuk itu kita akan menggunakan paket stringr (dalam “alam semesta paket” yang sama dengan lubridate, yang akan kita bahas nanti).
Saat menganalisis data kita biasanya memiliki beberapa variabel untuk setiap individu: kita memerlukan “tabel” untuk mengumpulkannya. Pilihan paling langsung adalah matriks: gabungan variabel bertipe sama dan panjang yang sama.
Bayangkan kita memiliki tinggi dan berat badan 4 orang. Bagaimana cara membuat dataset dengan dua variabel tersebut?
Pilihan paling umum adalah menggunakan cbind(): menggabungkan (bind) vektor dalam bentuk kolom (c)
Kita juga dapat membangun matriks berdasarkan baris dengan fungsi rbind() (gabungkan - bind - berdasarkan baris - r), meskipun disarankan memiliki setiap variabel dalam kolom dan individu dalam baris sebagaimana yang akan kita lihat nanti.
View(matrix).Kita juga dapat “membalik” (matriks transpos) dengan t().
Dalam beberapa kasus kita ingin mendapatkan seluruh data untuk satu individu (baris tertentu tapi semua kolom) atau nilai dari satu variabel lengkap untuk semua individu (kolom tertentu tapi semua baris). Untuk itu, kita kosongkan salah satu indeks.
Kita juga dapat mendefinisikan matriks dari vektor numerik, menyusun ulang nilai-nilai dalam bentuk matriks (dengan mengetahui bahwa elemen-elemen ditempatkan berdasarkan kolom).
Dengan matriks sama seperti dengan vektor: saat kita menerapkan operasi aritmatika kita melakukannya elemen per elemen
Kita juga dapat melakukan operasi per kolom/baris tanpa loop dengan fungsi apply(), dan kita akan menunjukkan sebagai argumen
MARGIN = 1 untuk baris, MARGIN = 2 untuk kolom)Coba kerjakan latihan-latihan berikut tanpa melihat solusinya
📝 Modifikasi kode di bawah untuk mendefinisikan matriks x berisi satu-satu, dengan 3 baris dan 7 kolom.
📝 Pada matriks di atas, tambahkan 1 ke setiap angka dan bagi hasilnya dengan 5. Kemudian hitung transposnya.
📝 Mengapa kode di bawah ini mengembalikan pesan peringatan seperti itu?
📝 Definisikan matriks x <- matrix(1:12, nrow = 4). Kemudian dapatkan data individu pertama, data variabel ketiga, dan elemen (4, 1).
📝 Definisikan matriks dengan 2 variabel dan 3 individu sehingga setiap variabel mencatat tinggi dan umur 3 orang, di mana umur orang kedua tidak diketahui. Kemudian hitung rata-rata setiap variabel (kita harus mendapatkan angka!).
Array memiliki masalah yang sama dengan vektor: jika kita menggabungkan data dari tipe yang berbeda, integritas data terganggu karena akan dikonversi (lihat kode di bawah: umur dan TRUE/FALSE dikonversi ke teks).
ages single names
[1,] "14" "TRUE" "javi"
[2,] "24" NA "laura"
[3,] NA "FALSE" "lucía"
Untuk bekerja dengan variabel dari tipe yang berbeda kita memiliki di R yang dikenal sebagai data.frame: gabungan variabel dengan panjang sama tetapi dapat bertipe berbeda.
Karena sebuah data.frame sudah merupakan upaya membuat database, variabel bukan sekadar vektor matematika: mereka memiliki makna dan kita dapat (kita harus) memberikan nama yang mendeskripsikan maknanya.
Kita memiliki dataset pertama kita! (secara ketat kita belum bisa menyebutnya database, tetapi untuk saat ini tampilannya seperti itu). Kamu dapat memvisualisasikannya dengan mengetik namanya di konsol atau dengan View(table).
Jika kita ingin mengakses elemennya, karena ini data tabular, kita dapat mengaksesnya seperti di matriks (tidak disarankan): sekali lagi kita memiliki dua indeks (baris dan kolom, biarkan kosong yang tidak digunakan)
ages single names birth_date
2 24 NA laura 1992-04-01
[1] "javi" "laura" "lucía"
[1] 24

Tetapi juga memiliki keunggulan sebuah database: kita dapat mengakses variabel berdasarkan nama (disarankan karena variabel dapat berpindah posisi dan sekarang memiliki makna), dengan meletakkan nama tabel diikuti simbol $ (dengan tab, menu kolom untuk dipilih akan muncul).
names(): menampilkan nama-nama variabelJika kita sudah memiliki data dan ingin menambahkan kolom, cukup gunakan fungsi data.frame() yang sudah kita pelajari untuk menggabungkan kolom. Mari tambahkan misalnya variabel baru, jumlah saudara kandung setiap individu.
Tabel dalam format data.frame memiliki beberapa keterbatasan. Keterbatasan utamanya adalah tidak mengizinkan rekursi: bayangkan kita mendefinisikan database dengan tinggi dan berat badan, dan kita ingin variabel ketiga berupa BMI.
Error: object 'weight' not found
Selanjutnya kita akan menggunakan format tibble (data.frame yang disempurnakan) dari paket tibble.
[1] "tbl_df" "tbl" "data.frame"
# A tibble: 3 × 3
height weight BMI
<dbl> <dbl> <dbl>
1 1.7 80 27.7
2 1.8 75 23.1
3 1.6 70 27.3
Tabel dalam format tibble memungkinkan kita pengelolaan data yang lebih cepat, efisien, dan konsisten, dengan 4 keunggulan utama:
tribble().Tip
Paket datapasta memungkinkan kita menyalin dan menempel tabel dari halaman web dan dokumen sederhana sebagai tribble. See more in https://milesmcbain.github.io/datapasta/articles/how-to-datapasta.html#pasting-a-table-as-a-formatted-tibble-definition-with-tribble_paste
R secara default operasi dilakukan elemen per elemen.Coba kerjakan latihan-latihan berikut tanpa melihat solusinya
📝 Muat dari paket {datasets} dataset airquality (variabel kualitas udara New York dari Mei hingga September 1973). Apakah dataset airquality bertipe tibble? Jika tidak, konversikan ke tibble (lihat dokumentasi paket di https://tibble.tidyverse.org/index.html).
📝 Setelah dikonversi ke tibble, dapatkan nama variabel dan dimensi dataset. Berapa banyak variabel? Berapa banyak hari yang telah diukur?
📝 Filter hanya data untuk bulan Agustus. Bagaimana cara menyampaikan bahwa kita hanya ingin baris yang memenuhi kondisi tertentu?
📝 Pilih data yang bukan dari bulan Juli atau Agustus.
📝 Modifikasi kode berikut untuk menyimpan hanya variabel ozon dan suhu (terlepas dari posisinya).
📝 Pilih data suhu dan angin untuk bulan Agustus.
Dalam paket {datasets} (sudah terinstal secara default) kita memiliki beberapa dataset, salah satunya adalah airquality. Di bawah ini saya mengekstrak 3 variabel dari dataset tersebut (perhatikan cara mengaksesnya dengan data$variable, simbol dolar akan penting ke depannya). Data ini merekam pengukuran harian (n = 153 observasi) kualitas udara di New York, dari Mei hingga September 1973. Enam 6 variabel diukur: kadar ozon, radiasi matahari, angin, suhu, bulan, dan hari.
Coba jawab pertanyaan-pertanyaan yang ada di workbook
Kita akan menggunakan file surveys.RData yang berisi semua survei jajak pendapat untuk Spanyol dari 1982 hingga 2019.
# A tibble: 139,944 × 8
date_elec pollster field_date_from field_date_to exit_poll size
<date> <chr> <date> <date> <lgl> <dbl>
1 1982-10-28 PSOE 1982-10-28 1982-10-28 TRUE 85300
2 1982-10-28 PSOE 1982-10-28 1982-10-28 TRUE 85300
3 1982-10-28 PSOE 1982-10-28 1982-10-28 TRUE 85300
4 1982-10-28 PSOE 1982-10-28 1982-10-28 TRUE 85300
5 1982-10-28 PSOE 1982-10-28 1982-10-28 TRUE 85300
6 1982-10-28 PSOE 1982-10-28 1982-10-28 TRUE 85300
7 1982-10-28 PSOE 1982-10-28 1982-10-28 TRUE 85300
8 1982-10-28 PSOE 1982-10-28 1982-10-28 TRUE 85300
9 1982-10-28 PSOE 1982-10-28 1982-10-28 TRUE 85300
10 1982-10-28 PSOE 1982-10-28 1982-10-28 TRUE 85300
# ℹ 139,934 more rows
# ℹ 2 more variables: party <chr>, estimation <dbl>
Coba jawab pertanyaan-pertanyaan yang ada di workbook
Struktur alur: if-else dan loop. Fungsi di R. Quarto
Sebuah struktur alur atau kontrol terdiri dari serangkaian perintah yang bertujuan untuk menentukan jalur yang harus diikuti kode kamu
Jika kondisi A terpenuhi, apa yang terjadi?
Bagaimana jika B terjadi?
Bagaimana saya bisa mengulang ekspresi yang sama (tergantung pada sebuah variabel)?
Jika kamu pernah membuat program sebelumnya, kamu mungkin sudah familiar dengan yang dikenal sebagai struktur kondisional seperti if (bla bla) {...} else {...} atau loop for/while (sedapat mungkin dihindari).
Salah satu struktur kontrol yang paling terkenal adalah yang dikenal sebagai struktur kondisional if.
JIKA serangkaian kondisi terpenuhi (TRUE), maka jalankan apa pun yang ada di dalam tanda kurung kurawal.
Misalnya, struktur if (x == 1) { code A } yang dilakukannya adalah menjalankan kode A dalam tanda kurung kurawal tetapi HANYA JIKA kondisi dalam tanda kurung benar (hanya jika x adalah 1). Dalam kasus lain, tidak akan melakukan apa-apa
Struktur kondisional kita akan melakukan hal berikut: jika ada yang di bawah umur, akan mencetak sebuah pesan.
Jika kondisi tidak benar di dalam if() (FALSE), tidak ada yang terjadi.
Kita tidak mendapat pesan karena kondisi all(ages >= 18) bukan TRUE, sehingga tidak mengeksekusi apa-apa.
Struktur if (condition) { code A } dapat digabungkan dengan else { code B }: ketika kondisi tidak terpenuhi, ia akan menjalankan kode alternatif B di dalam else { }, memungkinkan kita memutuskan apa yang terjadi ketika kondisi terpenuhi dan ketika tidak
Struktur if - else ini dapat ditumpuk: bayangkan kita ingin menjalankan kode jika semua di bawah umur; jika tidak, tetapi semua berumur di atas 16, lakukan hal lain; dalam kasus lainnya, lakukan tindakan lain.
[1] "There are any persons under 16 years of age"
Tips
Kamu bisa memperkecil struktur dengan mengklik panah kiri di script-mu.
Struktur kondisional ini dapat di-vektorisasi (dalam satu baris) dengan if_else() (dari paket dplyr), yang argumennya adalah
kondisi yang akan dievaluasi
apa yang terjadi ketika terpenuhi dan ketika tidak
argumen opsional untuk saat kondisi yang dievaluasi adalah NA
Kita akan memberi label bukan lebih besar/lebih kecil dan unknown ketika tidak diketahui.
Attaching package: 'dplyr'
The following objects are masked from 'package:stats':
filter, lag
The following objects are masked from 'package:base':
intersect, setdiff, setequal, union
[1] "unknown" "minor" "minor" "legal age" "legal age"
[6] "legal age" "legal age" "legal age" "legal age"
Dalam R base ada ifelse(): tidak memungkinkan kamu menentukan apa yang harus dilakukan dengan yang tidak ada, tetapi memungkinkan menentukan tipe data yang berbeda dalam TRUE dan FALSE.
Coba kerjakan latihan-latihan berikut tanpa melihat solusinya
📝 Apa yang akan menjadi output dari kode berikut?
📝 Apa yang akan menjadi output dari kode berikut?
📝 Modifikasi kode di bawah sehingga, ketika akar kuadrat suatu angka tidak dapat diverifikasi kurang dari 2, mengembalikan -1.
📝 Apa nilai x dan y dari kode di bawah untuk z <- 1, z <- -1, dan z <- -5?
📝 Apa yang akan terjadi jika kita menjalankan kode di bawah ini?
Salah satu kekuatan utama R adalah kemudahan menghasilkan laporan, buku, web, catatan, bahkan slide (materi ini sendiri misalnya). Untuk itu, instal terlebih dahulu
Sejauh ini kita hanya membuat program dalam skrip (file .R) dalam proyek, tetapi dalam banyak kesempatan kita tidak akan bekerja sendiri dan kita perlu mengkomunikasikan hasilnya dalam berbagai format:
Untuk semua ini kita akan menggunakan Quarto (lihat lebih lanjut di https://ivelasq.quarto.pub/intro-to-quarto/)
File dengan ekstensi .qmd (atau .rmd sebelumnya) akan memungkinkan kita dengan mudah menggabungkan:- Markdown:
R, Python, C++, Julia, …), dengan kotak kode yang disebut CHUNK.Keunggulan utama membuat materi semacam ini di Quarto/Rmarkdown adalah, dengan melakukannya dari RStudio, kamu dapat membuat laporan atau presentasi tanpa meninggalkan lingkungan pemrograman tempat kamu bekerja. Dengan cara ini kamu dapat menganalisis data, merangkumnya dan sekaligus mengkomunikasikannya dengan alat yang sama.
Baru-baru ini tim RStudio mengembangkan Quarto, versi yang disempurnakan dari Rmarkdown (file .qmd), dengan format yang sedikit lebih estetik dan sederhana. Semua dokumentasi dan contoh tersedia di https://quarto.org/
Gambar diperoleh dari https://ivelasq.quarto.pub/intro-to-quarto/#/working-with-the-rstudio-visual-editor

Kita akan membuat file rmarkdown pertama dengan Quarto berekstensi .qmd. Untuk itu kita hanya perlu mengklik
File << New File << Quarto Document

Setelah itu, beberapa pilihan format output:
File .pdf
.html file (recommendable): dynamic document, allows user interaction, like a “web page”.
File .doc (tidak disarankan).

Kamu seharusnya memiliki sesuatu yang mirip dengan tangkapan gambar dengan dua mode pengeditan: Source (dengan kode, pilihan yang disarankan sampai kamu menguasainya) dan Visual (lebih seperti blog).
Untuk menjalankan SELURUH dokumen kamu harus mengklik Render on Save dan menyimpannya.
Kamu seharusnya mendapatkan output html yang serupa ini (dan sebuah file html telah dibuat di komputermu).
Seperti yang ditunjukkan, kamu memiliki dua cara bekerja: dengan kode murni dan sesuatu yang mirip dengan Notion (blog).
Gambar diambil dari https://ivelasq.quarto.pub/intro-to-quarto/#/working-with-the-rstudio-visual-editor

File .qmd pada dasarnya dibagi menjadi tiga bagian:
Header: bagian yang ada di awal di antara ---.
Teks: yang dapat kita format dan perkuat dengan tebal (ditulis sebagai tebal, dengan tanda bintang ganda di awal dan akhir), miring (miring, dengan garis bawah di awal dan akhir) atau menyorot nama fungsi atau variabel dari R. Kamu dapat menambahkan persamaan seperti \(x^2\) (saya menulisnya $x^2$, di antara tanda dolar).
Kode R
The header dalam format YAML dan berisi metadata dari dokumen.
title dan subtitle: judul/subjudul dokumenauthor: penulis dokumenformat: format output (dapat dikustomisasi)
theme: jika memiliki file gayatoc: apakah ingin daftar isi atau tidaktoc-location: posisi daftar isitoc-title: judul daftar isieditor: apakah dalam mode visual atau source.The header dalam format YAML dan berisi metadata dari dokumen.
title dan subtitle: judul/subjudul dokumenauthor: penulis dokumenformat: format output (dapat dikustomisasi)
theme: jika memiliki file gayatoc: apakah ingin daftar isi atau tidaktoc-location: posisi daftar isitoc-title: judul daftar isieditor: apakah dalam mode visual atau source.The header dalam format YAML dan berisi metadata dari dokumen.
title dan subtitle: judul/subjudul dokumenauthor: penulis dokumenformat: format output (dapat dikustomisasi)
theme: jika memiliki file gayatoc: apakah ingin daftar isi atau tidaktoc-location: posisi daftar isitoc-title: judul daftar isieditor: apakah dalam mode visual atau source.The header dalam format YAML dan berisi metadata dari dokumen.
title dan subtitle: judul/subjudul dokumenauthor: penulis dokumenformat: format output (dapat dikustomisasi)
theme: jika memiliki file gayatoc: apakah ingin daftar isi atau tidaktoc-location: posisi daftar isitoc-title: judul daftar isieditor: apakah dalam mode visual atau source.The header dalam format YAML dan berisi metadata dari dokumen.
title dan subtitle: judul/subjudul dokumenauthor: penulis dokumenformat: format output (dapat dikustomisasi)
theme: jika memiliki file gayatoc: apakah ingin daftar isi atau tidaktoc-location: posisi daftar isitoc-title: judul daftar isieditor: apakah dalam mode visual atau source.Mengenai pengetikan hanya ada satu hal penting: kecuali kita tunjukkan sebaliknya, SEMUA yang akan kita ketikkan adalah teks (biasa); bukan kode R.


Kita akan mulai dengan menulis sebuah bagian di awal (# Intro dan di belakangnya, misalnya kalimat
Materi ini telah dirancang oleh Profesor nama penulis, profesor di Universitas Complutense Madrid
Selain Running Code kita akan menambahkan tanda #: tanda di luar chunk akan membantu kita membuat judul bagian dalam dokumen.


Agar daftar isi menangkap bagian-bagian tersebut kita akan memodifikasi header file seperti yang ditunjukkan pada gambar (kamu dapat mengubah lokasi daftar isi dan judulnya jika ingin mencoba).
Mari kita sesuaikan teks sedikit dengan melakukan hal berikut:


Kita akan menambahkan tebal pada nama (menambahkan ** di awal dan di akhir).
Kita akan menambahkan miring pada kata material (menambahkan _ di awal dan di akhir).
Kita akan menambahkan tautan https://www.ucm.es, menghubungkannya ke nama Universitas. Untuk itu kita menaruh judul dalam tanda kurung siku dan di belakangnya tautan dalam tanda kurung [“Universidad Complutense de Madrid”](https://www.ucm.es).
Untuk memasukkan kode R kita harus membuat kotak kode yang disebut chunk: ditempatkan dalam teks markdown kita di mana kita dapat memasukkan kode dari hampir semua bahasa (beserta outputnya).

Untuk memasukkan chunk, gunakan pintasan Command + Option + I (Mac) atau Ctrl + Shift + I (Windows)
Di dalam kotak ini (yang kini memiliki warna berbeda dalam dokumen) tuliskan kode R seperti yang sudah kita lakukan sejauh ini dalam skrip.


Chunk dapat memiliki nama atau tag, sehingga kita dapat mereferensikannya kembali untuk menghindari pengulangan kode.


Di setiap chunk terdapat dua tombol:
Tombol play: mengaktifkan jalankan dan keluarkan chunk tertentu tersebut (kamu dapat melihatnya di dalam RStudio-mu sendiri)
Tombol rewind: mengaktifkan jalankan dan keluarkan semua chunk hingga chunk tersebut (tanpa mencapainya).
Selain itu kita dapat memasukkan kode R di dalam baris teks (alih-alih menampilkan teks x jalankan kode R yang menampilkan variabel).
Chunk dapat dikustomisasi dengan opsi di awal chunk yang didahului #|:
#| echo: false: jalankan kode dan tampilkan hasil tetapi tidak menampilkan kode di output.
#| include: false: menjalankan kode tetapi tidak menampilkan hasil dan tidak menampilkan kode di output.
#| eval: false: tidak menjalankan kode, tidak menampilkan hasil tetapi menampilkan kode di output.
#| message: false: menjalankan kode tetapi tidak menampilkan pesan output.
#| warning: false: menjalankan kode tetapi tidak menampilkan pesan peringatan.
#| error: true: menjalankan kode dan mengizinkan error menampilkan pesan error di output.
Opsi-opsi ini dapat diterapkan per chunk atau diatur secara global dengan knitr::opts_chunk$set() di awal dokumen (dalam sebuah chunk).
Jika kita ingin menerapkan opsi ke semua chunk secara default kita harus menyertakannya di akhir header, sebagai opsi eksekusi
Selain teks dan kode kita dapat memasukkan hal berikut:
Persamaan: kamu juga dapat menambahkan persamaan seperti \(x^2\) (saya menulisnya $x^2$, persamaan di antara tanda dolar).
Daftar: kamu dapat membuat daftar elemen dengan meletakkan * Langkah 1: ... *Langkah 2: ...
Referensi silang: kamu dapat menandai bagian dokumen (tag dibuat dengan {#section-name}) dan kemudian memanggil dengan [Bagian](@section-name).


Akhirnya, kita juga dapat menambahkan keterangan pada grafik atau gambar dengan menambahkan #| fig-cap: "...".
Perhatikan bahwa keterangan ada di margin (misalnya). Kamu dapat mengubahnya dengan memasukkan pengaturan header (semua tentang gambar dimulai dengan fig-, dan kamu dapat melihat opsinya dengan menekan tab). Info lebih lanjut di https://quarto.org/



Akhirnya kamu dapat menambahkan tema kustom termasuk sebuah file gaya (file .scss atau .css). Saya telah menyediakan satu untuk kamu di https://github.com/dadosdelaplace/docencia-R-master-bio-2324/tree/main/material.
Penting
File gaya harus berada di folder yang sama dengan file .qmd.
Kamu juga dapat melakukannya dengan cara sederhana menambahkan sedikit HTML ke teks. Misalnya, untuk mengkustomisasi warna teks, letakkan di antara tanda kurung siku dan tepat setelah teks, di antara tanda kurung kurawal, opsi gaya tersebut
This word is red …
… and this is green in bold
Kamu dapat menambahkan “animasi” menggunakan Revealjs (javascript), menentukannya di header dan menggunakan blok bahasa tersebut yang dibatasi ::: di awal dan akhir. Contohnya {.incremental} mentransisikan elemen-elemen.
Kamu juga dapat menggunakan callout-blocks yang secara default adalah note, tip, warning, caution dan important (meskipun kamu dapat membuat dan mengkustomisasinya). Untuk itu, gunakan saja ::{.callout-type} dan tipe yang ingin digunakan
Tip
Perhatikan ada lima jenis callout: note, tip, warning, caution, dan important.
Caution
Gunakan dengan bijaksana; terlalu banyak elemen visual kadang membingungkan.
Dengan :::: columns kita dapat mendefinisikan tata letak beberapa kolom di mana masing-masing didefinisikan oleh ::: {.column width="65%"} sesuatu :::, menunjukkan persentase yang diinginkan setiap kolom (hati-hati jangan ada spasi!).
Selain itu reticulate memungkinkan kita membuat chunk python di dalam Quarto di R (lihat https://quarto.org/docs/computations/python.html untuk membuat jupyter notebook langsung dari Quarto).
To practice control structures we are going to perform a simulation exercise
Coba jawab pertanyaan-pertanyaan yang ada di workbook
Definisikan fungsi bernama temperature_converter yang, diberikan suhu dalam Fahrenheit, Celsius, atau Kelvin, mengonversinya ke salah satu yang lain
Coba jawab pertanyaan-pertanyaan yang ada di workbook
Mari lakukan simulasi kecil sebelum pengumpulan menggunakan dataset starwars dari paket dplyr.
# A tibble: 87 × 14
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 Luke… 172 77 blond fair blue 19 male
2 C-3PO 167 75 <NA> gold yellow 112 none
3 R2-D2 96 32 <NA> white, bl… red 33 none
4 Dart… 202 136 none white yellow 41.9 male
5 Leia… 150 49 brown light brown 19 fema…
6 Owen… 178 120 brown, gr… light blue 52 male
7 Beru… 165 75 brown light blue 47 fema…
8 R5-D4 97 32 <NA> white, red red NA none
9 Bigg… 183 84 black light brown 24 male
10 Obi-… 182 77 auburn, w… fair blue-gray 57 male
# ℹ 77 more rows
# ℹ 6 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>
Kita memiliki berbagai variabel karakter Star Wars, dengan karakteristik rambut, kulit, tinggi, nama, dll.
Buat dokumen
.qmddengan nama, judul, format, dan indeks. Setiap Latihan berikutnya akan menjadi subbagian dokumen. Jalankan chunk yang diperlukan dan beri komentar pada output untuk menjawab setiap pertanyaan
Latihan 1. Berapa banyak karakter dalam database? Berapa banyak karakteristik yang diukur?
Latihan 2. Ekstrak variabel
namesdanagesdari tabel. Tipe apa variabel name? Dan variabel birth_year?
Latihan 3. Dapatkan vektor nama karakter diurutkan dari tertua ke termuda.
Latihan 4. Gunakan fungsi unique() untuk mengetahui modalitas variabel kualitatif warna mata. Berapa banyak yang berbeda?
Latihan 5. Apakah ada nilai yang hilang dalam variabel warna mata?
Latihan 6. Hitung rata-rata dan simpangan baku variabel tinggi dan berat (perhatikan nilai hilang). Definisikan tibble baru dan tambahkan variabel “BMI” untuk menghitung indeks massa tubuh. Sertakan formula BMI dengan
$ $.
Pada hari pengumpulan kamu akan memiliki template pengumpulan dalam format .qmd di kampus.
Ekstrak foldernya (penting! jika tidak diekstrak, meskipun bisa mengedit .qmd, kamu tidak akan bisa menghasilkan .html)
Edit header dengan nama dan NIM-mu
Kamu harus mengisi setiap chunk dengan kode yang sesuai (di beberapa saya telah meninggalkan petunjuk) dan mengubah dari #| eval: false ke #| eval: true (jika dihapus langsung, secara default sudah true)
Kamu harus mengomentari dengan teks biasa apa yang kamu anggap sebagai jawaban atas pertanyaan-pertanyaan tersebut.
WAJIB mengumpulkan file .html yang dihasilkan (hanya file itu yang akan dinilai), jadi render seiring mengisi dokumen, jangan tunggu sampai akhir.
Format favorit kita: tibble. Tidyverse: alam semesta tidy data
Format database akhir kita akan menjadi objek tipe tibble, sebuah data.frame yang disempurnakan.
# A tibble: 3 × 3
height weight BMI
<dbl> <dbl> <dbl>
1 1.7 80 27.7
2 1.8 75 23.1
3 1.6 70 27.3
Metainformasi: di header secara otomatis menampilkan jumlah baris dan kolom, serta tipe setiap variabel.
Rekursivitas: memungkinkan mendefinisikan variabel secara berurutan (seperti yang sudah kita lihat).
Konsistensi: jika mengakses kolom yang tidak ada, akan memberikan peringatan.
Berdasarkan baris: memungkinkan membuat berdasarkan baris dengan tribble().
Untuk mendefinisikan tibble() sendiri kita memiliki dua opsi:
Sejauh ini, semua yang telah kita lakukan di R dilakukan dalam paradigma pemrograman yang dikenal sebagai R base. Ketika R lahir sebagai bahasa, banyak yang memprogram di dalamnya meniru bentuk dan metodologi yang diwarisi dari bahasa lain, berdasarkan penggunaan
Loop for dan while
Tanda dolar $ untuk mengakses variabel
Struktur if-else
Dan meskipun mengetahui struktur-struktur ini bisa menarik dalam beberapa kasus, dalam sebagian besar kasus mereka sudah usang dan kita akan dapat menghindarinya (terutama loop) karena R dirancang khusus untuk bekerja secara fungsional (bukan elemen-per-elemen).


Dalam konteks pemrograman fungsional ini, satu dekade lalu lahirlah tidyverse, sebuah “alam semesta” paket untuk menjamin alur kerja yang efisien, koheren, dan sederhana, berdasarkan ide bahwa data kita bersih dan rapi.


Dataset yang rapi semuanya serupa, tetapi setiap dataset yang berantakan memiliki cara berantakannya sendiri (Hadley Wickham, Ilmuwan Kepala di RStudio)
TIDYVERSE
Alam semesta paket tidyverse didasarkan pada ide yang diperkenalkan oleh Hadley Wickham (sang maestro) tentang standarisasi format data untuk
Hal pertama yang harus dipahami adalah apa itu dataset tidydata, karena seluruh tidyverse didasarkan pada data yang terstandarisasi.

Dalam tidyverse operator pipe (pipa) yang didefinisikan sebagai |> (ctrl+shift+M) akan menjadi kunci: ini adalah pipa yang melewati data dan mengubahnya. . . .
Dalam R base, jika kita ingin menerapkan tiga fungsi first(), second() dan third() secara berurutan, itu akan menjadi
Dalam tidyverse kita dapat membaca dari kiri ke kanan dan memisahkan data dari tindakan
Penting
Sejak versi 4.1.0 R kita memiliki |>, sebuah pipe native yang tersedia di luar tidyverse, menggantikan pipe lama %>% yang bergantung pada paket magrittr (cukup bermasalah).
Keunggulan utamanya adalah kode sangat mudah dibaca (hampir literal) dan kamu dapat melakukan operasi besar pada data dengan kode yang sangat sedikit.
Tapi seperti apa data yang tidak rapi (berantakan) itu? Mari muat tabel table4a dari paket tidyr (sudah dimuat dari lingkungan tidyverse).
# A tibble: 3 × 3
country `1999` `2000`
<chr> <dbl> <dbl>
1 Afghanistan 745 2666
2 Brazil 37737 80488
3 China 212258 213766
Apa yang mungkin salah?
❎ Setiap baris merepresentasikan dua pengamatan (1999 dan 2000) → kolom 1999 dan 2000 seharusnya menjadi nilai dari sebuah variabel bukan nama kolom.
Kita akan menyertakan kolom baru yang menyimpan tahun dan kolom lain yang menyimpan nilai variabel yang diminati di setiap tahun. Dan kita akan melakukannya dengan fungsi pivot_longer(): pivot tabel ke format panjang:

cols: nama variabel yang akan di-pivot.names_to: nama variabel baru ke mana kita mengirim header tabel (nama-namanya).values_to: nama variabel baru ke mana kita akan mengirim data.Mari lihat contoh lain dengan tabel table2.
# A tibble: 12 × 4
country year type count
<chr> <dbl> <chr> <dbl>
1 Afghanistan 1999 cases 745
2 Afghanistan 1999 population 19987071
3 Afghanistan 2000 cases 2666
4 Afghanistan 2000 population 20595360
5 Brazil 1999 cases 37737
6 Brazil 1999 population 172006362
7 Brazil 2000 cases 80488
8 Brazil 2000 population 174504898
9 China 1999 cases 212258
10 China 1999 population 1272915272
11 China 2000 cases 213766
12 China 2000 population 1280428583
Apa yang mungkin salah?
# A tibble: 12 × 4
country year type count
<chr> <dbl> <chr> <dbl>
1 Afghanistan 1999 cases 745
2 Afghanistan 1999 population 19987071
3 Afghanistan 2000 cases 2666
4 Afghanistan 2000 population 20595360
5 Brazil 1999 cases 37737
6 Brazil 1999 population 172006362
7 Brazil 2000 cases 80488
8 Brazil 2000 population 174504898
9 China 1999 cases 212258
10 China 1999 population 1272915272
11 China 2000 cases 213766
12 China 2000 population 1280428583
❎ Setiap pengamatan dibagi dalam dua baris → catatan dengan tahun yang sama seharusnya sama
Yang akan kita lakukan adalah kebalikannya: dengan pivot_wider() kita akan memperlebar tabel
# A tibble: 6 × 4
country year cases population
<chr> <dbl> <dbl> <dbl>
1 Afghanistan 1999 745 19987071
2 Afghanistan 2000 2666 20595360
3 Brazil 1999 37737 172006362
4 Brazil 2000 80488 174504898
5 China 1999 212258 1272915272
6 China 2000 213766 1280428583
Mari lihat contoh lain dengan tabel table3.
# A tibble: 6 × 3
country year rate
<chr> <dbl> <chr>
1 Afghanistan 1999 745/19987071
2 Afghanistan 2000 2666/20595360
3 Brazil 1999 37737/172006362
4 Brazil 2000 80488/174504898
5 China 1999 212258/1272915272
6 China 2000 213766/1280428583
Apa yang mungkin salah?
❎ Setiap sel berisi beberapa nilai
Yang akan kita lakukan adalah menggunakan fungsi separate() untuk memisahkan setiap nilai ke kolom yang berbeda.
# A tibble: 6 × 4
country year cases pop
<chr> <dbl> <chr> <chr>
1 Afghanistan 1999 745 19987071
2 Afghanistan 2000 2666 20595360
3 Brazil 1999 37737 172006362
4 Brazil 2000 80488 174504898
5 China 1999 212258 1272915272
6 China 2000 213766 1280428583
# A tibble: 6 × 4
country year cases pop
<chr> <dbl> <chr> <chr>
1 Afghanistan 1999 745 19987071
2 Afghanistan 2000 2666 20595360
3 Brazil 1999 37737 172006362
4 Brazil 2000 80488 174504898
5 China 1999 212258 1272915272
6 China 2000 213766 1280428583
Perhatikan bahwa data, meskipun sudah dipisahkan, tetap sebagai teks padahal seharusnya berupa variabel numerik. Untuk itu kita dapat menambahkan argumen opsional convert = TRUE.
# A tibble: 6 × 4
country year cases pop
<chr> <dbl> <int> <int>
1 Afghanistan 1999 745 19987071
2 Afghanistan 2000 2666 20595360
3 Brazil 1999 37737 172006362
4 Brazil 2000 80488 174504898
5 China 1999 212258 1272915272
6 China 2000 213766 1280428583
Mari lihat contoh terakhir dengan tabel table5.
# A tibble: 6 × 4
country century year rate
<chr> <chr> <chr> <chr>
1 Afghanistan 19 99 745/19987071
2 Afghanistan 20 00 2666/20595360
3 Brazil 19 99 37737/172006362
4 Brazil 20 00 80488/174504898
5 China 19 99 212258/1272915272
6 China 20 00 213766/1280428583
Apa yang mungkin salah?
❎ Kita memiliki nilai yang sama yang dibagi dalam dua kolom
Kita akan menggunakan unite() untuk menyatukan nilai abad dan tahun dalam kolom yang sama
# A tibble: 6 × 3
country whole_year rate
<chr> <chr> <chr>
1 Afghanistan 1999 745/19987071
2 Afghanistan 2000 2666/20595360
3 Brazil 1999 37737/172006362
4 Brazil 2000 80488/174504898
5 China 1999 212258/1272915272
6 China 2000 213766/1280428583
Kita juga dapat menyarangkan dataset di dalam dataset lain: bayangkan kita memiliki dataset dengan variabel x dan y, dengan dua catatan, satu lagi dengan satu catatan, dan satu lagi dengan 3 catatan.
# A tibble: 6 × 3
dataset x y
<dbl> <dbl> <dbl>
1 1 0 -1
2 1 2 NA
3 2 NA 5
4 3 -2 1.5
5 3 6 NA
6 3 7 -2
Pada kenyataannya, semua yang memiliki nilai sama dalam dataset harus membentuk tibble-nya sendiri, jadi mari buat satu di dalam yang kita miliki
Untuk itu kita akan menggunakan fungsi nest() dengan menunjukkan variabel mana yang membentuk dataset yang akan disarangkan (dalam kasus ini variabel x dan y). Perhatikan bahwa yang disimpan di dalamnya adalah variabel bertipe list (karena setiap dataset memiliki panjang yang berbeda).
Untuk membuka sarang cukup gunakan fungsi unnest() dengan menunjukkan kolom yang akan dibuka sarangnya.
Dalam paket tidyr kita memiliki dataset world_bank_pop yang berisi data dari Bank Dunia tentang populasi per negara dari tahun 2000 hingga 2018.
# A tibble: 1,064 × 20
country indicator `2000` `2001` `2002` `2003` `2004` `2005`
<chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
1 ABW SP.URB.TOTL 4.16e4 4.20e+4 4.22e+4 4.23e+4 4.23e+4 4.24e+4
2 ABW SP.URB.GROW 1.66e0 9.56e-1 4.01e-1 1.97e-1 9.46e-2 1.94e-1
3 ABW SP.POP.TOTL 8.91e4 9.07e+4 9.18e+4 9.27e+4 9.35e+4 9.45e+4
4 ABW SP.POP.GROW 2.54e0 1.77e+0 1.19e+0 9.97e-1 9.01e-1 1.00e+0
5 AFE SP.URB.TOTL 1.16e8 1.20e+8 1.24e+8 1.29e+8 1.34e+8 1.39e+8
6 AFE SP.URB.GROW 3.60e0 3.66e+0 3.72e+0 3.71e+0 3.74e+0 3.81e+0
7 AFE SP.POP.TOTL 4.02e8 4.12e+8 4.23e+8 4.34e+8 4.45e+8 4.57e+8
8 AFE SP.POP.GROW 2.58e0 2.59e+0 2.61e+0 2.62e+0 2.64e+0 2.67e+0
9 AFG SP.URB.TOTL 4.31e6 4.36e+6 4.67e+6 5.06e+6 5.30e+6 5.54e+6
10 AFG SP.URB.GROW 1.86e0 1.15e+0 6.86e+0 7.95e+0 4.59e+0 4.47e+0
# ℹ 1,054 more rows
# ℹ 12 more variables: `2006` <dbl>, `2007` <dbl>, `2008` <dbl>,
# `2009` <dbl>, `2010` <dbl>, `2011` <dbl>, `2012` <dbl>,
# `2013` <dbl>, `2014` <dbl>, `2015` <dbl>, `2016` <dbl>,
# `2017` <dbl>
Apa yang mungkin salah?
Pertama-tama, kita dapat melihat bahwa kita secara efektif memiliki variabel yang sama dalam 18 kolom: populasi.
Yang seharusnya kita miliki adalah kolom bernama pop dengan nilai-nilai ini dan kolom lain year yang menunjukkan tahun yang sesuai dengan pengukuran. Dan untuk itu kita akan menggunakan pivot_longer().
# A tibble: 19,152 × 4
country indicator year value
<chr> <chr> <chr> <dbl>
1 ABW SP.URB.TOTL 2000 41625
2 ABW SP.URB.TOTL 2001 42025
3 ABW SP.URB.TOTL 2002 42194
4 ABW SP.URB.TOTL 2003 42277
5 ABW SP.URB.TOTL 2004 42317
6 ABW SP.URB.TOTL 2005 42399
7 ABW SP.URB.TOTL 2006 42555
8 ABW SP.URB.TOTL 2007 42729
9 ABW SP.URB.TOTL 2008 42906
10 ABW SP.URB.TOTL 2009 43079
# ℹ 19,142 more rows
# A tibble: 19,152 × 4
country indicator year value
<chr> <chr> <chr> <dbl>
1 ABW SP.URB.TOTL 2000 41625
2 ABW SP.URB.TOTL 2001 42025
3 ABW SP.URB.TOTL 2002 42194
4 ABW SP.URB.TOTL 2003 42277
5 ABW SP.URB.TOTL 2004 42317
6 ABW SP.URB.TOTL 2005 42399
7 ABW SP.URB.TOTL 2006 42555
8 ABW SP.URB.TOTL 2007 42729
9 ABW SP.URB.TOTL 2008 42906
10 ABW SP.URB.TOTL 2009 43079
# ℹ 19,142 more rows
Apakah semuanya sudah benar?
Jika kamu perhatikan kita memiliki dua jenis ukuran populasi, total ...TOTL dan pertumbuhannya ...GROW, selain itu kita memilikinya untuk setiap negara secara global SP.POP... dan hanya di area perkotaan SP.URB....
Apa yang harus dilakukan?
Kita akan memisahkan variabel ini menjadi 3: satu untuk awalan SP (yang akan kita hapus nanti), satu untuk area (POP/URB) dan satu untuk nilai (variable), yang bisa berupa total atau pertumbuhan.
# A tibble: 19,152 × 5
country area variable year value
<chr> <chr> <chr> <chr> <dbl>
1 ABW URB TOTL 2000 41625
2 ABW URB TOTL 2001 42025
3 ABW URB TOTL 2002 42194
4 ABW URB TOTL 2003 42277
5 ABW URB TOTL 2004 42317
6 ABW URB TOTL 2005 42399
7 ABW URB TOTL 2006 42555
8 ABW URB TOTL 2007 42729
9 ABW URB TOTL 2008 42906
10 ABW URB TOTL 2009 43079
# ℹ 19,142 more rows
Ini dapat dilakukan dengan cara yang lebih sederhana dengan menunjukkan dalam variabel yang ingin kita hapus bahwa nilainya adalah NA di dalam separate().
# A tibble: 19,152 × 5
country area variable year value
<chr> <chr> <chr> <chr> <dbl>
1 ABW URB TOTL 2000 41625
2 ABW URB TOTL 2001 42025
3 ABW URB TOTL 2002 42194
4 ABW URB TOTL 2003 42277
5 ABW URB TOTL 2004 42317
6 ABW URB TOTL 2005 42399
7 ABW URB TOTL 2006 42555
8 ABW URB TOTL 2007 42729
9 ABW URB TOTL 2008 42906
10 ABW URB TOTL 2009 43079
# ℹ 19,142 more rows
Apakah kita sudah berhasil? Pikirkan dengan cermat: apakah setiap variabel memiliki kolomnya sendiri?
Jika kamu benar-benar melihat variabel total populasi dan pertumbuhan, mereka seharusnya menjadi variabel yang berbeda, karena bahkan memiliki satuan yang berbeda: satu adalah penduduk, yang lain adalah poin persentase.
Untuk melakukan kebalikan dari operasi awal, gunakan pivot_wider() (nanti kita akan menggunakan fungsi yang sangat berguna, clean_names() dari janitor yang menyatukan nama variabel).
# A tibble: 9,576 × 5
country area year totl grow
<chr> <chr> <chr> <dbl> <dbl>
1 ABW URB 2000 41625 1.66
2 ABW URB 2001 42025 0.956
3 ABW URB 2002 42194 0.401
4 ABW URB 2003 42277 0.197
5 ABW URB 2004 42317 0.0946
6 ABW URB 2005 42399 0.194
7 ABW URB 2006 42555 0.367
8 ABW URB 2007 42729 0.408
9 ABW URB 2008 42906 0.413
10 ABW URB 2009 43079 0.402
# ℹ 9,566 more rows
Kode lengkapnya akan seperti ini: singkat, padat, mudah dibaca, dan mendeskripsikan dirinya sendiri.
# A tibble: 9,576 × 5
country area year totl grow
<chr> <chr> <chr> <dbl> <dbl>
1 ABW URB 2000 41625 1.66
2 ABW URB 2001 42025 0.956
3 ABW URB 2002 42194 0.401
4 ABW URB 2003 42277 0.197
5 ABW URB 2004 42317 0.0946
6 ABW URB 2005 42399 0.194
7 ABW URB 2006 42555 0.367
8 ABW URB 2007 42729 0.408
9 ABW URB 2008 42906 0.413
10 ABW URB 2009 43079 0.402
# ℹ 9,566 more rows
Dalam paket tidyr kita memiliki dataset who2 (dataset Organisasi Kesehatan Dunia)
# A tibble: 7,240 × 58
country year sp_m_014 sp_m_1524 sp_m_2534 sp_m_3544 sp_m_4554
<chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
1 Afghanistan 1980 NA NA NA NA NA
2 Afghanistan 1981 NA NA NA NA NA
3 Afghanistan 1982 NA NA NA NA NA
4 Afghanistan 1983 NA NA NA NA NA
5 Afghanistan 1984 NA NA NA NA NA
6 Afghanistan 1985 NA NA NA NA NA
7 Afghanistan 1986 NA NA NA NA NA
8 Afghanistan 1987 NA NA NA NA NA
9 Afghanistan 1988 NA NA NA NA NA
10 Afghanistan 1989 NA NA NA NA NA
# ℹ 7,230 more rows
# ℹ 51 more variables: sp_m_5564 <dbl>, sp_m_65 <dbl>,
# sp_f_014 <dbl>, sp_f_1524 <dbl>, sp_f_2534 <dbl>,
# sp_f_3544 <dbl>, sp_f_4554 <dbl>, sp_f_5564 <dbl>, sp_f_65 <dbl>,
# sn_m_014 <dbl>, sn_m_1524 <dbl>, sn_m_2534 <dbl>,
# sn_m_3544 <dbl>, sn_m_4554 <dbl>, sn_m_5564 <dbl>, sn_m_65 <dbl>,
# sn_f_014 <dbl>, sn_f_1524 <dbl>, sn_f_2534 <dbl>, …
Apakah ini tidy data? Mengapa?
Langkah pertama untuk tidy data: kita harus me-pivot tabel (tips: gunakan kertas dan pena untuk membuat sketsa tampilan database yang seharusnya) sehingga ada kolom bernama cases (karena semua kolom mulai dari year sebenarnya sama, kasus suatu penyakit).
# A tibble: 405,440 × 4
country year type cases
<chr> <dbl> <chr> <dbl>
1 Afghanistan 1980 sp_m_014 NA
2 Afghanistan 1980 sp_m_1524 NA
3 Afghanistan 1980 sp_m_2534 NA
4 Afghanistan 1980 sp_m_3544 NA
5 Afghanistan 1980 sp_m_4554 NA
6 Afghanistan 1980 sp_m_5564 NA
7 Afghanistan 1980 sp_m_65 NA
8 Afghanistan 1980 sp_f_014 NA
9 Afghanistan 1980 sp_f_1524 NA
10 Afghanistan 1980 sp_f_2534 NA
# ℹ 405,430 more rows
Jika kamu perhatikan, ada banyak baris yang tidak masuk akal untuk disimpan karena kita tidak memiliki kasus! Investigasi opsi pivot_longer() untuk melihat bagaimana kita dapat langsung menghapusnya dalam pivot.
# A tibble: 76,046 × 4
country year type cases
<chr> <dbl> <chr> <dbl>
1 Afghanistan 1997 sp_m_014 0
2 Afghanistan 1997 sp_m_1524 10
3 Afghanistan 1997 sp_m_2534 6
4 Afghanistan 1997 sp_m_3544 3
5 Afghanistan 1997 sp_m_4554 5
6 Afghanistan 1997 sp_m_5564 2
7 Afghanistan 1997 sp_m_65 0
8 Afghanistan 1997 sp_f_014 5
9 Afghanistan 1997 sp_f_1524 38
10 Afghanistan 1997 sp_f_2534 36
# ℹ 76,036 more rows
Sekarang dalam type kita mengkodekan informasi sebagai diagnosis_sex_age. Bagaimana memisahkannya menjadi 3 kolom? Investigasi opsi separate() dan pivot_longer().
# A tibble: 76,046 × 6
country year diagnosis sex age cases
<chr> <dbl> <chr> <chr> <chr> <dbl>
1 Afghanistan 1997 sp m 014 0
2 Afghanistan 1997 sp m 1524 10
3 Afghanistan 1997 sp m 2534 6
4 Afghanistan 1997 sp m 3544 3
5 Afghanistan 1997 sp m 4554 5
6 Afghanistan 1997 sp m 5564 2
7 Afghanistan 1997 sp m 65 0
8 Afghanistan 1997 sp f 014 5
9 Afghanistan 1997 sp f 1524 38
10 Afghanistan 1997 sp f 2534 36
# ℹ 76,036 more rows
Terakhir, pisahkan menjadi dua (age_inf, age_sup) rentang usia (yang berupa angka). Pikirkan cara melakukannya karena tidak selalu 4 angka (jika tidak ada batas atas usia yang ditentukan, masukkan Inf sebagai batas atas).
# A tibble: 76,046 × 7
country year diagnosis sex age_inf age_sup cases
<chr> <dbl> <chr> <chr> <dbl> <dbl> <dbl>
1 Afghanistan 1997 sp m 0 14 0
2 Afghanistan 1997 sp m 15 24 10
3 Afghanistan 1997 sp m 25 34 6
4 Afghanistan 1997 sp m 35 44 3
5 Afghanistan 1997 sp m 45 54 5
6 Afghanistan 1997 sp m 55 64 2
7 Afghanistan 1997 sp m 65 Inf 0
8 Afghanistan 1997 sp f 0 14 5
9 Afghanistan 1997 sp f 15 24 38
10 Afghanistan 1997 sp f 25 34 36
# ℹ 76,036 more rows
Coba kerjakan latihan-latihan berikut tanpa melihat solusinya
📝 Gunakan dataset who2 asli dari tidyr dan jawab: berapa kasus tuberkulosis di Spanyol tahun 1995 di kalangan perempuan? Lakukan tanpa mengonversi ke tidydata, lalu dengan tidydata, dan bandingkan keterbacaan kodenya.
# messy data
sum(who2[who2$country == "Spain" & who2$year == 1995,
names(who2)[str_detect(names(who2), "f_")]], na.rm = TRUE)
# tidy data (at this moment)
sum(who_tidy[who_tidy$country == "Spain" &
who_tidy$year == 1995 &
who_tidy$sex == "f", ]$cases)
# in the future
who_tidy |>
filter(country == "Spain" & year == 1995 & sex == "f") |>
summarise(sum(cases))📝 Menggunakan who_tidy tentukan jenis kelamin mana yang memiliki lebih banyak kasus, pria atau wanita? Buat variabel baru avg_age: jika rentang 25–34, rata-rata umur \((25+34)/2 = 29.5\) (jika Inf di atas, NA).
📝 Jika harus memilih negara dengan probabilitas infeksi terendah, negara mana antara Inggris Raya dan Prancis yang memiliki kasus paling sedikit di tahun terbaru?
📝 Lihat tabel table4b dalam paket tidyr. Apakah ini tidydata? Jika tidak, apa yang salah dan bagaimana mengonversinya?
📝 Lihat tabel billboard dalam paket tidyr. Apakah ini tidydata? Jika tidak, apa yang salah dan bagaimana mengonversinya?
Mari lakukan studi kasus dengan tabel relig_income dalam paket tidyr. Tabel ini merepresentasikan jumlah orang dalam setiap kelompok pendapatan tahunan (20k = $20.000) dan setiap agama.
Coba jawab pertanyaan-pertanyaan yang ada di workbook
Tidyverse: tindakan berdasarkan baris
Dalam tidyverse kita akan menggunakan paket dplyr untuk proses pra-pemrosesan data.

Idenya adalah agar kode semudah mungkin dibaca, seolah-olah merupakan daftar instruksi yang saat dibaca memberitahu kita secara jelas apa yang sedang dilakukan.
Semua proses pra-pemrosesan yang akan kita lakukan berasumsi bahwa data kita sudah dalam format tidydata

Ingat bahwa dalam tidyverse, operator pipe yang didefinisikan sebagai |> (ctrl+shift+M) akan menjadi kunci: ini adalah pipe yang melewati data dan mengubahnya.
Mari berlatih dengan dataset starwars dari paket dplyr.
Salah satu operasi paling umum adalah yang dikenal dalam statistik sebagai pengambilan sampel: sebuah pemilihan atau penyaringan catatan (baris) (subsampel).

filter()).slice()).slice_sample()).group_by() + slice_sample()).Tindakan paling sederhana berdasarkan baris adalah saat menyaring catatan berdasarkan kondisi logika: dengan filter() hanya individu yang memenuhi kondisi tertentu yang akan dipilih (pengambilan sampel non-acak berdasarkan kondisi).
==, !=: sama dengan atau berbeda dari (|> filter(variable == "a"))>, <: lebih besar atau lebih kecil dari (|> filter(variable < 3))>=, <=: lebih besar atau sama dengan atau lebih kecil atau sama dengan (|> filter(variable >= 5))%in%: nilai termasuk dalam sekumpulan opsi diskrit (|> filter(variable %in% c("blue", "green")))between(variable, val1, val2): jika nilai kontinu berada dalam rentang (|> filter(between(variable, 160, 180)))Kondisi logika ini dapat digabungkan dalam berbagai cara (dan, atau, atau saling eksklusif).
Penting
Ingat bahwa di dalam filter() harus selalu ada sesuatu yang mengembalikan vektor nilai logika.
Bagaimana cara… menyaring karakter dengan mata coklat?
Tipe variabel apa itu? –> Variabel eye_color bersifat kualitatif sehingga diwakili oleh teks.
# A tibble: 21 × 14
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 Leia… 150 49 brown light brown 19 fema…
2 Bigg… 183 84 black light brown 24 male
3 Han … 180 80 brown fair brown 29 male
4 Yoda 66 17 white green brown 896 male
5 Boba… 183 78.2 black fair brown 31.5 male
6 Land… 177 79 black dark brown 31 male
7 Arve… NA NA brown fair brown NA male
8 Wick… 88 20 brown brown brown 8 male
9 Padm… 185 45 brown light brown 46 fema…
10 Quar… 183 NA black dark brown 62 male
# ℹ 11 more rows
# ℹ 6 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>
Bagaimana cara… menyaring karakter yang tidak memiliki mata coklat?
# A tibble: 66 × 14
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 Luke… 172 77 blond fair blue 19 male
2 C-3PO 167 75 <NA> gold yellow 112 none
3 R2-D2 96 32 <NA> white, bl… red 33 none
4 Dart… 202 136 none white yellow 41.9 male
5 Owen… 178 120 brown, gr… light blue 52 male
6 Beru… 165 75 brown light blue 47 fema…
7 R5-D4 97 32 <NA> white, red red NA none
8 Obi-… 182 77 auburn, w… fair blue-gray 57 male
9 Anak… 188 84 blond fair blue 41.9 male
10 Wilh… 180 NA auburn, g… fair blue 64 male
# ℹ 56 more rows
# ℹ 6 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>
Bagaimana cara… menyaring karakter yang memiliki mata coklat atau biru?
# A tibble: 40 × 14
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 Luke… 172 77 blond fair blue 19 male
2 Leia… 150 49 brown light brown 19 fema…
3 Owen… 178 120 brown, gr… light blue 52 male
4 Beru… 165 75 brown light blue 47 fema…
5 Bigg… 183 84 black light brown 24 male
6 Anak… 188 84 blond fair blue 41.9 male
7 Wilh… 180 NA auburn, g… fair blue 64 male
8 Chew… 228 112 brown unknown blue 200 male
9 Han … 180 80 brown fair brown 29 male
10 Jek … 180 110 brown fair blue NA <NA>
# ℹ 30 more rows
# ℹ 6 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>
Perhatikan bahwa %in% setara dengan menggabungkan beberapa == dengan konjungsi atau (|)
# A tibble: 40 × 14
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 Luke… 172 77 blond fair blue 19 male
2 Leia… 150 49 brown light brown 19 fema…
3 Owen… 178 120 brown, gr… light blue 52 male
4 Beru… 165 75 brown light blue 47 fema…
5 Bigg… 183 84 black light brown 24 male
6 Anak… 188 84 blond fair blue 41.9 male
7 Wilh… 180 NA auburn, g… fair blue 64 male
8 Chew… 228 112 brown unknown blue 200 male
9 Han … 180 80 brown fair brown 29 male
10 Jek … 180 110 brown fair blue NA <NA>
# ℹ 30 more rows
# ℹ 6 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>
Bagaimana cara… menyaring karakter yang tingginya antara 120 dan 160 cm?
Tipe variabel apa itu? –> Variabel height adalah variabel kuantitatif kontinu sehingga kita harus memfilter berdasarkan rentang nilai (interval) –> gunakan between().
# A tibble: 6 × 14
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 Leia … 150 49 brown light brown 19 fema…
2 Mon M… 150 NA auburn fair blue 48 fema…
3 Nien … 160 68 none grey black NA male
4 Watto 137 NA black blue, grey yellow NA male
5 Gasga… 122 NA none white, bl… black NA male
6 Cordé 157 NA brown light brown NA <NA>
# ℹ 6 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>
Bagaimana cara… menyaring karakter yang bermata coklat dan bukan manusia?
# A tibble: 3 × 14
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 Yoda 66 17 white green brown 896 male
2 Wicke… 88 20 brown brown brown 8 male
3 Eeth … 171 NA black brown brown NA male
# ℹ 6 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>
Bagaimana cara… menyaring karakter yang bermata coklat dan bukan manusia, atau berumur lebih dari 60 tahun? Pikirkan: tanda kurung itu penting: \((a+b)*c\) tidak sama dengan \(a+(b*c)\).
# A tibble: 18 × 14
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 C-3PO 167 75 <NA> gold yellow 112 none
2 Wilh… 180 NA auburn, g… fair blue 64 male
3 Chew… 228 112 brown unknown blue 200 male
4 Jabb… 175 1358 <NA> green-tan… orange 600 herm…
5 Yoda 66 17 white green brown 896 male
6 Palp… 170 75 grey pale yellow 82 male
7 Wick… 88 20 brown brown brown 8 male
8 Qui-… 193 89 brown fair blue 92 male
9 Fini… 170 NA blond fair blue 91 male
10 Quar… 183 NA black dark brown 62 male
11 Shmi… 163 NA black fair brown 72 fema…
12 Mace… 188 84 none dark brown 72 male
13 Ki-A… 198 82 white pale yellow 92 male
14 Eeth… 171 NA black brown brown NA male
15 Clie… 183 NA brown fair blue 82 male
16 Dooku 193 80 white fair brown 102 male
17 Bail… 191 NA black tan brown 67 male
18 Jang… 183 79 black tan brown 66 male
# ℹ 6 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>
There is a special filter for one of the most common operations in debugging: remove absent. For this we can use inside a filter is.na(), which returns TRUE/FALSE debelum disiapkan on whether it is absent, or …
Gunakan drop_na(): jika kita tidak menentukan variabel, catatan dengan nilai hilang di variabel mana pun akan dihapus. Nanti kita akan melihat cara mengimputasi nilai hilang tersebut
# A tibble: 7 × 4
name mass height hair_color
<chr> <dbl> <int> <chr>
1 Luke Skywalker 77 172 blond
2 C-3PO 75 167 <NA>
3 R2-D2 32 96 <NA>
4 Darth Vader 136 202 none
5 Leia Organa 49 150 brown
6 Owen Lars 120 178 brown, grey
7 Beru Whitesun Lars 75 165 brown
# A tibble: 7 × 4
name mass height hair_color
<chr> <dbl> <int> <chr>
1 Luke Skywalker 77 172 blond
2 Darth Vader 136 202 none
3 Leia Organa 49 150 brown
4 Owen Lars 120 178 brown, grey
5 Beru Whitesun Lars 75 165 brown
6 Biggs Darklighter 84 183 black
7 Obi-Wan Kenobi 77 182 auburn, white
Coba kerjakan latihan-latihan berikut tanpa melihat solusinya
📝 Pilih dari dataset starwars hanya karakter yang merupakan android atau yang nilai species-nya tidak diketahui.
📝 Pilih dari dataset starwars hanya karakter yang beratnya antara 65 dan 90 kg.
📝 Setelah menghapus nilai hilang di semua variabel, pilih dari starwars hanya karakter yang manusia dan berasal dari Tatooine.
📝 Pilih dari starwars asli karakter yang bukan manusia, berjenis kelamin male, tinggi antara 120–170 cm, atau karakter dengan mata coklat atau merah.
Terkadang kita mungkin tertarik melakukan pengambilan sampel diskresioner non-acak, atau dengan kata lain, filter berdasarkan posisi: dengan slice(positions) kita dapat memilih baris tertentu dengan memberikan vektor indeks sebagai argumen.
# A tibble: 1 × 4
name height mass hair_color
<chr> <int> <dbl> <chr>
1 Luke Skywalker 172 77 blond
# A tibble: 4 × 8
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 C-3PO 167 75 <NA> gold yellow 112 none
2 Beru … 165 75 brown light blue 47 fema…
3 Obi-W… 182 77 auburn, w… fair blue-gray 57 male
4 Qui-G… 193 89 brown fair blue 92 male
Kita memiliki opsi default:
slice_head(n = ...) dan slice_tail(n = ...) kita dapat mengambil header dan ekor tabelKita memiliki opsi default:
slice_max() dan slice_min() kita mendapatkan baris dengan nilai terkecil/terbesar dari suatu variabel (jika seri, semuanya kecuali with_ties = FALSE) yang kita tunjukkan dalam order_by = ....# A tibble: 2 × 4
name height mass hair_color
<chr> <int> <dbl> <chr>
1 Ratts Tyerel 79 15 none
2 Yoda 66 17 white
Yang disebut pengambilan sampel acak sederhana didasarkan pada memilih individu secara acak, sehingga setiap individu memiliki probabilitas tertentu untuk dipilih. Dengan slice_sample(n = ...) kita dapat mengekstrak n catatan secara acak (a priori equiprobable).
# A tibble: 2 × 14
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 Mon M… 150 NA auburn fair blue 48 fema…
2 Poe D… NA NA brown light brown NA male
# ℹ 6 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>
Penting
“Acak” tidak berarti equiprobable: dadu biasa sama acaknya dengan dadu curang. Tidak ada hal yang “lebih acak” dari yang lain, mereka hanya memiliki hukum probabilitas dasar yang berbeda.
Kita juga dapat menunjukkan proporsi data yang akan diambil sampelnya (bukan jumlahnya) dan apakah kita ingin dengan penggantian (bisa terulang).
# A tibble: 4 × 14
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 Luke … 172 77 blond fair blue 19 male
2 Grega… 185 85 black dark brown NA <NA>
3 Poggl… 183 80 none green yellow NA male
4 Dud B… 94 45 none blue, grey yellow NA male
# ℹ 6 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>
Seperti yang sudah dikatakan, “acak” tidak sama dengan “equiprobable”, sehingga kita dapat meneruskan vektor probabilitas. Misalnya, mari paksa agar sangat tidak mungkin mengambil baris selain dua baris pertama
# A tibble: 2 × 14
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 C-3PO 167 75 <NA> gold yellow 112 none
2 Luke … 172 77 blond fair blue 19 male
# ℹ 6 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>
# A tibble: 2 × 14
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 C-3PO 167 75 <NA> gold yellow 112 none
2 Luke … 172 77 blond fair blue 19 male
# ℹ 6 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>
Fungsi slice_sample() hanyalah integrasi tidyverse dari fungsi dasar R yang dikenal sebagai sample() yang memungkinkan kita mengambil sampel elemen
Opsi sebelumnya menghasilkan kejadian dari variabel acak equiprobable tetapi seperti sebelumnya, kita dapat menetapkan vektor probabilitas atau fungsi massa kepadanya dengan argumen prob = ....
Bagaimana cara membuat pernyataan berikut?
Misalkan episode flu musiman telah dipelajari di sebuah kota. Biarkan \(X_m\) dan \(X_p\) menjadi variabel acak sedemikian rupa sehingga \(X_m=1\) jika ibu terkena flu, \(X_m=0\) jika ibu tidak terkena flu, \(X_p=1\) jika ayah terkena flu dan \(X_p=0\) jika ayah tidak terkena flu. Model teoritis yang terkait dengan jenis epidemi ini menunjukkan bahwa distribusi bersama diberikan oleh \(P(X_m = 1, X_p=1)=0.02\), \(P(X_m = 1, X_p=0)=0.08\), \(P(X_m = 1, X_p=0)=0.1\) dan \(P(X_m = 0, X_p=0)=0.8\)
Buat sampel berukuran \(n = 1000\) (dukungan "10", "01", "00" dan "11") menggunakan runif() dan menggunakan sample().
Kita juga dapat mengurutkan berdasarkan baris sesuai variabel tertentu dengan arrange().
# A tibble: 5 × 6
name height mass hair_color skin_color eye_color
<chr> <int> <dbl> <chr> <chr> <chr>
1 Ratts Tyerel 79 15 none grey, blue unknown
2 Yoda 66 17 white green brown
3 Wicket Systri Warrick 88 20 brown brown brown
4 R2-D2 96 32 <NA> white, blue red
5 R5-D4 97 32 <NA> white, red red
Secara dari terkecil ke terbesar tetapi kita dapat membalik urutannya dengan desc().
# A tibble: 5 × 3
name height mass
<chr> <int> <dbl>
1 Yarael Poof 264 NA
2 Tarfful 234 136
3 Lama Su 229 88
4 Chewbacca 228 112
5 Roos Tarpals 224 82
Berkali-kali kita perlu memastikan tidak ada duplikat dalam beberapa variabel dan kita dapat menghapus baris duplikat dengan distinct().
# A tibble: 5 × 1
sex
<chr>
1 male
2 none
3 female
4 hermaphroditic
5 <NA>
Untuk menyimpan semua kolom tabel kita akan menggunakan .keep_all = TRUE.
# A tibble: 3 × 14
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 Luke … 172 77 blond fair blue 19 male
2 C-3PO 167 75 <NA> gold yellow 112 none
3 Leia … 150 49 brown light brown 19 fema…
# ℹ 6 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>
Terakhir, kita dapat menambahkan baris baru dengan bind_rows() dengan pengamatan baru dalam tabel (jika kolom tidak cocok diisi dengan nilai hilang)
# A tibble: 2 × 2
name age
<chr> <dbl>
1 javi 33
2 laura 50
Coba kerjakan latihan-latihan berikut tanpa melihat solusinya
📝 Pilih hanya karakter manusia bermata coklat, lalu urutkan dari tinggi menurun dan berat menaik.
📝 Ambil 10 karakter secara acak sedemikian rupa sehingga probabilitas setiap karakter dipilih sebanding dengan beratnya (lebih berat, lebih mungkin terpilih).
📝 Untuk mengetahui nilai unik dalam warna rambut, hapus duplikat variabel hair_color dengan terlebih dahulu menghapus nilai yang hilang.
📝 Dari karakter manusia dengan tinggi >160 cm, hapus duplikat warna mata, hapus nilai hilang pada berat, pilih 3 tertinggi, dan urutkan dari berat terbesar ke terkecil.
Mari kembali ke dataset yang sudah dikenal: dalam paket {datasets} kita memiliki beberapa dataset, salah satunya airquality yang sudah kita kerjakan. Data ini merekam pengukuran harian (n = 153 observasi) kualitas udara di New York, Mei–September 1973.
Saat itu kita mengerjakannya dari perspektif R base. Tujuan sekarang adalah mengerjakannya dari perspektif tidyverse sambil melihat perbedaan antara kedua cara tersebut.
Coba jawab pertanyaan-pertanyaan yang ada di workbook.
Tidyverse: tindakan berdasarkan kolom
Hingga saat ini semua operasi yang dilakukan (meskipun menggunakan info kolom) adalah berdasarkan baris. Untuk kolom, tindakan paling sederhana adalah memilih variabel berdasarkan nama dengan select(), dengan memberikan nama kolom tanpa tanda kutip sebagai argumen.
# A tibble: 87 × 2
name hair_color
<chr> <chr>
1 Luke Skywalker blond
2 C-3PO <NA>
3 R2-D2 <NA>
4 Darth Vader none
5 Leia Organa brown
6 Owen Lars brown, grey
7 Beru Whitesun Lars brown
8 R5-D4 <NA>
9 Biggs Darklighter black
10 Obi-Wan Kenobi auburn, white
# ℹ 77 more rows
Fungsi select() memungkinkan memilih beberapa variabel sekaligus, termasuk menghubungkan nama-namanya seolah indeks numerik dengan :
# A tibble: 4 × 6
name height mass hair_color skin_color eye_color
<chr> <int> <dbl> <chr> <chr> <chr>
1 Luke Skywalker 172 77 blond fair blue
2 C-3PO 167 75 <NA> gold yellow
3 R2-D2 96 32 <NA> white, blue red
4 Darth Vader 202 136 none white yellow
Dan kita dapat membatalkan pilihan kolom dengan tanda - di depannya
# A tibble: 4 × 4
name height hair_color skin_color
<chr> <int> <chr> <chr>
1 Luke Skywalker 172 blond fair
2 C-3PO 167 <NA> gold
3 R2-D2 96 <NA> white, blue
4 Darth Vader 202 none white
Kita juga memiliki kata-kata khusus: everything() untuk semua variabel….
# A tibble: 4 × 14
mass homeworld name height hair_color skin_color eye_color
<dbl> <chr> <chr> <int> <chr> <chr> <chr>
1 77 Tatooine Luke Skywalk… 172 blond fair blue
2 75 Tatooine C-3PO 167 <NA> gold yellow
3 32 Naboo R2-D2 96 <NA> white, bl… red
4 136 Tatooine Darth Vader 202 none white yellow
# ℹ 7 more variables: birth_year <dbl>, sex <chr>, gender <chr>,
# species <chr>, films <list>, vehicles <list>, starships <list>
…and last_col() to refer to last column.
# A tibble: 4 × 5
name height mass homeworld starships
<chr> <int> <dbl> <chr> <list>
1 Luke Skywalker 172 77 Tatooine <chr [2]>
2 C-3PO 167 75 Tatooine <chr [0]>
3 R2-D2 96 32 Naboo <chr [0]>
4 Darth Vader 202 136 Tatooine <chr [1]>
Kita juga dapat bermain dengan pola dalam nama: yang dimulai dengan awalan (starts_with()), diakhiri dengan akhiran (ends_with()), mengandung teks (contains()), atau memenuhi ekspresi reguler (matches()).
# A tibble: 87 × 5
hair_color skin_color eye_color sex gender
<chr> <chr> <chr> <chr> <chr>
1 blond fair blue male masculine
2 <NA> gold yellow none masculine
3 <NA> white, blue red none masculine
4 none white yellow male masculine
5 brown light brown female feminine
6 brown, grey light blue male masculine
7 brown light blue female feminine
8 <NA> white, red red none masculine
9 black light brown male masculine
10 auburn, white fair blue-gray male masculine
# ℹ 77 more rows
Kita bahkan dapat memilih berdasarkan rentang numerik jika memiliki variabel dengan awalan dan angka.
Terakhir, kita dapat memilih kolom berdasarkan tipe data menggunakan where() dan fungsi yang mengembalikan nilai logika berdasarkan tipe data.
# A tibble: 87 × 11
height mass birth_year name hair_color skin_color eye_color sex
<int> <dbl> <dbl> <chr> <chr> <chr> <chr> <chr>
1 172 77 19 Luke… blond fair blue male
2 167 75 112 C-3PO <NA> gold yellow none
3 96 32 33 R2-D2 <NA> white, bl… red none
4 202 136 41.9 Dart… none white yellow male
5 150 49 19 Leia… brown light brown fema…
6 178 120 52 Owen… brown, gr… light blue male
7 165 75 47 Beru… brown light blue fema…
8 97 32 NA R5-D4 <NA> white, red red none
9 183 84 24 Bigg… black light brown male
10 182 77 57 Obi-… auburn, w… fair blue-gray male
# ℹ 77 more rows
# ℹ 3 more variables: gender <chr>, homeworld <chr>, species <chr>
Untuk memfasilitasi pemindahan variabel kita memiliki fungsinya, relocate(), dengan menunjukkan di .after atau .before di belakang atau di depan kolom mana kita ingin memindahkannya.
# A tibble: 87 × 14
species name height mass hair_color skin_color eye_color
<chr> <chr> <int> <dbl> <chr> <chr> <chr>
1 Human Luke Skywalker 172 77 blond fair blue
2 Droid C-3PO 167 75 <NA> gold yellow
3 Droid R2-D2 96 32 <NA> white, bl… red
4 Human Darth Vader 202 136 none white yellow
5 Human Leia Organa 150 49 brown light brown
6 Human Owen Lars 178 120 brown, gr… light blue
7 Human Beru Whitesun… 165 75 brown light blue
8 Droid R5-D4 97 32 <NA> white, red red
9 Human Biggs Darklig… 183 84 black light brown
10 Human Obi-Wan Kenobi 182 77 auburn, w… fair blue-gray
# ℹ 77 more rows
# ℹ 7 more variables: birth_year <dbl>, sex <chr>, gender <chr>,
# homeworld <chr>, films <list>, vehicles <list>, starships <list>
Terkadang kita juga ingin memodifikasi “meta-informasi” data, mengganti nama kolom. Gunakan rename() dengan mengetikkan nama baru terlebih dahulu lalu nama lama.
# A tibble: 87 × 14
nombre altura peso hair_color skin_color eye_color birth_year
<chr> <int> <dbl> <chr> <chr> <chr> <dbl>
1 Luke Skywa… 172 77 blond fair blue 19
2 C-3PO 167 75 <NA> gold yellow 112
3 R2-D2 96 32 <NA> white, bl… red 33
4 Darth Vader 202 136 none white yellow 41.9
5 Leia Organa 150 49 brown light brown 19
6 Owen Lars 178 120 brown, gr… light blue 52
7 Beru White… 165 75 brown light blue 47
8 R5-D4 97 32 <NA> white, red red NA
9 Biggs Dark… 183 84 black light brown 24
10 Obi-Wan Ke… 182 77 auburn, w… fair blue-gray 57
# ℹ 77 more rows
# ℹ 7 more variables: sex <chr>, gender <chr>, homeworld <chr>,
# species <chr>, films <list>, vehicles <list>, starships <list>
Jika melihat output dari select(), itu masih berupa tabel tibble, mempertahankan sifat data kita.
Terkadang kita tidak menginginkan struktur seperti itu, melainkan mengekstrak kolom secara harfiah sebagai VEKTOR, yang dapat dilakukan dengan pull().
[1] "Luke Skywalker" "C-3PO"
[3] "R2-D2" "Darth Vader"
[5] "Leia Organa" "Owen Lars"
[7] "Beru Whitesun Lars" "R5-D4"
[9] "Biggs Darklighter" "Obi-Wan Kenobi"
[11] "Anakin Skywalker" "Wilhuff Tarkin"
[13] "Chewbacca" "Han Solo"
[15] "Greedo" "Jabba Desilijic Tiure"
[17] "Wedge Antilles" "Jek Tono Porkins"
[19] "Yoda" "Palpatine"
[21] "Boba Fett" "IG-88"
[23] "Bossk" "Lando Calrissian"
[25] "Lobot" "Ackbar"
[27] "Mon Mothma" "Arvel Crynyd"
[29] "Wicket Systri Warrick" "Nien Nunb"
[31] "Qui-Gon Jinn" "Nute Gunray"
[33] "Finis Valorum" "Padmé Amidala"
[35] "Jar Jar Binks" "Roos Tarpals"
[37] "Rugor Nass" "Ric Olié"
[39] "Watto" "Sebulba"
[41] "Quarsh Panaka" "Shmi Skywalker"
[43] "Darth Maul" "Bib Fortuna"
[45] "Ayla Secura" "Ratts Tyerel"
[47] "Dud Bolt" "Gasgano"
[49] "Ben Quadinaros" "Mace Windu"
[51] "Ki-Adi-Mundi" "Kit Fisto"
[53] "Eeth Koth" "Adi Gallia"
[55] "Saesee Tiin" "Yarael Poof"
[57] "Plo Koon" "Mas Amedda"
[59] "Gregar Typho" "Cordé"
[61] "Cliegg Lars" "Poggle the Lesser"
[63] "Luminara Unduli" "Barriss Offee"
[65] "Dormé" "Dooku"
[67] "Bail Prestor Organa" "Jango Fett"
[69] "Zam Wesell" "Dexter Jettster"
[71] "Lama Su" "Taun We"
[73] "Jocasta Nu" "R4-P17"
[75] "Wat Tambor" "San Hill"
[77] "Shaak Ti" "Grievous"
[79] "Tarfful" "Raymus Antilles"
[81] "Sly Moore" "Tion Medon"
[83] "Finn" "Rey"
[85] "Poe Dameron" "BB8"
[87] "Captain Phasma"
Coba kerjakan latihan-latihan berikut tanpa melihat solusinya
📝 Filter karakter dan simpan hanya yang tidak memiliki data hilang pada variabel height. Dengan data tersebut, pilih hanya variabel name, height, serta semua variabel yang MENGANDUNG kata color dalam namanya.
📝 Dengan data dari latihan sebelumnya, terjemahkan nama kolom ke dalam bahasa Indonesia.
📝 Dengan data dari Latihan 1, tempatkan variabel warna rambut tepat setelah variabel nama.
Con los data obtenidos del Exercise anterior, coloca la variable de color de pelo justo detrás de la variable de nombres.
📝 Dengan data dari Latihan 1, periksa berapa banyak modalitas unik dalam variabel warna rambut (tanpa menggunakan unique()).
📝 Dari dataset asli, hapus kolom bertipe list, lalu hapus duplikat pada variabel eye_color. Setelah menghapus duplikat, ekstrak kolom tersebut ke dalam vektor.
📝 Dari dataset starwars asli, hanya dengan karakter yang tingginya diketahui, ekstrak variabel tersebut ke dalam vektor.
📝 Setelah mendapatkan vektor dari latihan sebelumnya, gunakan vektor ini untuk mengambil sampel acak 50% data sehingga probabilitas karakter dipilih berbanding terbalik dengan tingginya (lebih pendek, lebih banyak kemungkinan).
Dalam banyak kesempatan kita ingin memodifikasi atau membuat variabel dengan mutate().
Misalnya mari buat variabel baru height_m dengan tinggi dalam meter.
# A tibble: 87 × 15
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 Luke… 172 77 blond fair blue 19 male
2 C-3PO 167 75 <NA> gold yellow 112 none
3 R2-D2 96 32 <NA> white, bl… red 33 none
4 Dart… 202 136 none white yellow 41.9 male
5 Leia… 150 49 brown light brown 19 fema…
6 Owen… 178 120 brown, gr… light blue 52 male
7 Beru… 165 75 brown light blue 47 fema…
8 R5-D4 97 32 <NA> white, red red NA none
9 Bigg… 183 84 black light brown 24 male
10 Obi-… 182 77 auburn, w… fair blue-gray 57 male
# ℹ 77 more rows
# ℹ 7 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>, height_m <dbl>
Selain itu dengan argumen opsional kita dapat memposisikan ulang kolom yang dimodifikasi
# A tibble: 87 × 16
height_m BMI name height mass hair_color skin_color eye_color
<dbl> <dbl> <chr> <int> <dbl> <chr> <chr> <chr>
1 1.72 26.0 Luke S… 172 77 blond fair blue
2 1.67 26.9 C-3PO 167 75 <NA> gold yellow
3 0.96 34.7 R2-D2 96 32 <NA> white, bl… red
4 2.02 33.3 Darth … 202 136 none white yellow
5 1.5 21.8 Leia O… 150 49 brown light brown
6 1.78 37.9 Owen L… 178 120 brown, gr… light blue
7 1.65 27.5 Beru W… 165 75 brown light blue
8 0.97 34.0 R5-D4 97 32 <NA> white, red red
9 1.83 25.1 Biggs … 183 84 black light brown
10 1.82 23.2 Obi-Wa… 182 77 auburn, w… fair blue-gray
# ℹ 77 more rows
# ℹ 8 more variables: birth_year <dbl>, sex <chr>, gender <chr>,
# homeworld <chr>, species <chr>, films <list>, vehicles <list>,
# starships <list>
Penting
Saat menerapkan mutate(), ingat bahwa operasi dilakukan vektor per vektor, elemen per elemen, sehingga fungsi yang digunakan harus mengembalikan vektor dengan panjang yang sama. Jika tidak, akan mengembalikan konstanta.
# A tibble: 87 × 15
constante name height mass hair_color skin_color eye_color
<dbl> <chr> <int> <dbl> <chr> <chr> <chr>
1 97.3 Luke Skywal… 172 77 blond fair blue
2 97.3 C-3PO 167 75 <NA> gold yellow
3 97.3 R2-D2 96 32 <NA> white, bl… red
4 97.3 Darth Vader 202 136 none white yellow
5 97.3 Leia Organa 150 49 brown light brown
6 97.3 Owen Lars 178 120 brown, gr… light blue
7 97.3 Beru Whites… 165 75 brown light blue
8 97.3 R5-D4 97 32 <NA> white, red red
9 97.3 Biggs Darkl… 183 84 black light brown
10 97.3 Obi-Wan Ken… 182 77 auburn, w… fair blue-gray
# ℹ 77 more rows
# ℹ 8 more variables: birth_year <dbl>, sex <chr>, gender <chr>,
# homeworld <chr>, species <chr>, films <list>, vehicles <list>,
# starships <list>
Kita juga dapat menggabungkan mutate() dengan ekspresi kontrol if_else() untuk mengkategorikan ulang variabel: jika kondisi terpenuhi, lakukan satu hal, jika tidak lakukan hal lain.
# A tibble: 87 × 4
name human height mass
<chr> <chr> <int> <dbl>
1 Luke Skywalker Human 172 77
2 C-3PO Not Human 167 75
3 R2-D2 Not Human 96 32
4 Darth Vader Human 202 136
5 Leia Organa Human 150 49
6 Owen Lars Human 178 120
7 Beru Whitesun Lars Human 165 75
8 R5-D4 Not Human 97 32
9 Biggs Darklighter Human 183 84
10 Obi-Wan Kenobi Human 182 77
# ℹ 77 more rows
Untuk kategorisasi yang lebih kompleks kita memiliki case_when(), misalnya untuk membuat kategori karakter berdasarkan tinggi badannya.
# A tibble: 81 × 15
altura name height mass hair_color skin_color eye_color
<chr> <chr> <int> <dbl> <chr> <chr> <chr>
1 normal Luke Skywalker 172 77 blond fair blue
2 normal C-3PO 167 75 <NA> gold yellow
3 dwarf R2-D2 96 32 <NA> white, bl… red
4 giant Darth Vader 202 136 none white yellow
5 short Leia Organa 150 49 brown light brown
6 normal Owen Lars 178 120 brown, gr… light blue
7 normal Beru Whitesun … 165 75 brown light blue
8 dwarf R5-D4 97 32 <NA> white, red red
9 tall Biggs Darkligh… 183 84 black light brown
10 tall Obi-Wan Kenobi 182 77 auburn, w… fair blue-gray
# ℹ 71 more rows
# ℹ 8 more variables: birth_year <dbl>, sex <chr>, gender <chr>,
# homeworld <chr>, species <chr>, films <list>, vehicles <list>,
# starships <list>
Kita juga dapat menyarangkan atau menyematkan dataset satu sama lain. Bayangkan kita memiliki dataset variabel x dan y dengan 2 catatan, satu lagi dengan satu catatan, dan satu lagi dengan 3 catatan.
Sejauh ini satu-satunya cara yang kita tahu untuk menggabungkan 3 dataset adalah menggunakan bind_rows() (ngomong-ngomong, jika menggunakan argumen .id = "nama_variabel" kita dapat membuatnya menambahkan variabel baru yang memberi tahu dataset asal setiap baris).
# A tibble: 6 × 3
dataset x y
<chr> <dbl> <dbl>
1 1 0 -1
2 1 2 NA
3 2 NA 5
4 3 -2 1.5
5 3 6 NA
6 3 7 -2
Namun, dalam banyak kesempatan kita ingin memiliki ketiganya dalam objek yang sama TETAPI setiap dataset tersendiri: sebuah objek (list) yang menyimpan 3 dataset terpisah
# A tibble: 3 × 2
dataset data
<chr> <list>
1 1 <tibble [2 × 2]>
2 2 <tibble [1 × 2]>
3 3 <tibble [3 × 2]>
Perhatikan bahwa sekarang data_nest adalah list karena setiap dataset yang disimpan bisa memiliki panjang yang berbeda
Untuk membuka sarang gunakan unnest() dengan menunjukkan kolom yang berisi dataset
Coba kerjakan latihan-latihan berikut tanpa melihat solusinya
📝 Pilih hanya variabel name, height, dan semua variabel terkait warna, sambil menyimpan hanya yang tidak memiliki nilai hilang pada height.
📝 Dengan data dari latihan sebelumnya, terjemahkan nama kolom ke dalam bahasa Indonesia.
📝 Dengan data dari latihan sebelumnya, tempatkan variabel warna rambut tepat setelah variabel nama.
📝 Dengan data asli, periksa berapa banyak modalitas unik dalam variabel warna rambut.
📝 Dari dataset asli, pilih hanya variabel numerik dan teks. Kemudian definisikan variabel baru bernama under_18: TRUE jika di bawah umur dan FALSE jika tidak.
📝 Dari dataset asli, buat kolom baru bernama auburn yang bernilai TRUE jika warna rambut mengandung kata itu dan FALSE jika tidak (ingat str_detect()).
📝 Dari dataset asli, tambahkan kolom yang menghitung BMI. Kemudian buat variabel baru bernilai NA jika bukan manusia, underweight jika BMI <18, normal jika 18–30, overweight jika >30.
belum disiapkan to submit
Coba jawab pertanyaan-pertanyaan yang ada di workbook.
Mari kembali ke analisis lagu-lagu Taylor Swift yang kita lakukan sebelumnya.
# A tibble: 240 × 29
album_name ep album_release track_number track_name artist
<chr> <lgl> <date> <int> <chr> <chr>
1 Taylor Swift FALSE 2006-10-24 1 Tim McGraw Taylo…
2 Taylor Swift FALSE 2006-10-24 2 Picture To Bu… Taylo…
3 Taylor Swift FALSE 2006-10-24 3 Teardrops On … Taylo…
4 Taylor Swift FALSE 2006-10-24 4 A Place In Th… Taylo…
5 Taylor Swift FALSE 2006-10-24 5 Cold As You Taylo…
6 Taylor Swift FALSE 2006-10-24 6 The Outside Taylo…
7 Taylor Swift FALSE 2006-10-24 7 Tied Together… Taylo…
8 Taylor Swift FALSE 2006-10-24 8 Stay Beautiful Taylo…
9 Taylor Swift FALSE 2006-10-24 9 Should've Sai… Taylo…
10 Taylor Swift FALSE 2006-10-24 10 Mary's Song (… Taylo…
# ℹ 230 more rows
# ℹ 23 more variables: featuring <chr>, bonus_track <lgl>,
# promotional_release <date>, single_release <date>,
# track_release <date>, danceability <dbl>, energy <dbl>,
# key <int>, loudness <dbl>, mode <int>, speechiness <dbl>,
# acousticness <dbl>, instrumentalness <dbl>, liveness <dbl>,
# valence <dbl>, tempo <dbl>, time_signature <int>, …
Perbedaannya adalah sekarang kita mencoba melakukan segalanya dari sudut pandang tidyverse bukan R base (menarik jika kamu mencoba menerjemahkan dari satu ke yang lain untuk menguasai kedua sudut pandang).
Coba jawab pertanyaan-pertanyaan yang ada di workbook.
Untuk berlatih beberapa fungsi dplyr kita akan menggunakan data dari film trilogi Lord of the Rings. Kita akan memuat data langsung dari web (Github dalam kasus ini), tanpa mengunduh terlebih dahulu, cukup menunjukkan tautan web sebagai path.
The Fellowship of the Ring -> https://raw.githubusercontent.com/jennybc/lotr-tidy/master/data/The_Fellowship_Of_The_Ring.csv
The 2 Towers -> https://raw.githubusercontent.com/jennybc/lotr-tidy/master/data/The_Two_Towers.csv
The Return of the King -> https://raw.githubusercontent.com/jennybc/lotr-tidy/master/data/The_Return_Of_The_King.csv.
Rows: 3 Columns: 4
── Column specification ──────────────────────────────────────────────
Delimiter: ","
chr (2): Film, Race
dbl (2): Female, Male
ℹ Use `spec()` to retrieve the full column specification for this data.
ℹ Specify the column types or set `show_col_types = FALSE` to quiet this message.
Rows: 3 Columns: 4
── Column specification ──────────────────────────────────────────────
Delimiter: ","
chr (2): Film, Race
dbl (2): Female, Male
ℹ Use `spec()` to retrieve the full column specification for this data.
ℹ Specify the column types or set `show_col_types = FALSE` to quiet this message.
Rows: 3 Columns: 4
── Column specification ──────────────────────────────────────────────
Delimiter: ","
chr (2): Film, Race
dbl (2): Female, Male
ℹ Use `spec()` to retrieve the full column specification for this data.
ℹ Specify the column types or set `show_col_types = FALSE` to quiet this message.
Coba jawab pertanyaan-pertanyaan yang ada di workbook.
Summarise dan group_by(). Menghitung dan merangkum
Sejauh ini kita hanya mengubah atau meminta data tetapi belum menghasilkan statistik. Mari mulai dengan yang sederhana: bagaimana cara menghitung (frekuensi)?
Ketika digunakan sendiri count() hanya mengembalikan jumlah catatan, tetapi ketika digunakan dengan variabel, dihitung yang dikenal sebagai frekuensi: jumlah elemen setiap modalitas.
Jika kita meneruskan beberapa variabel, dihitung yang dikenal sebagai tabel kontingensi. Dengan sort = TRUE akan mengembalikan hitungan terurut (yang paling sering pertama).
Salah satu fungsi paling kuat untuk digabungkan dengan tindakan yang sudah dipelajari adalah group_by(), yang memungkinkan kita mengelompokkan catatan terlebih dahulu.
Saat menerapkan group_by() penting dipahami bahwa itu TIDAK MEMODIFIKASI data, tetapi membuat variabel grup (sub-tabel untuk setiap grup) yang akan memodifikasi tindakan mendatang: operasi akan diterapkan pada setiap sub-tabel secara terpisah
Misalnya, bayangkan kita ingin mengekstrak karakter tertinggi dengan slice_max().
# A tibble: 1 × 14
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 Yarae… 264 NA none white yellow NA male
# ℹ 6 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>
Bagaimana jika kita ingin mengekstrak karakter tertinggi tetapi…dari masing-masing jenis kelamin?
# A tibble: 5 × 14
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 Taun … 213 NA none grey black NA fema…
2 Jabba… 175 1358 <NA> green-tan… orange 600 herm…
3 Yarae… 264 NA none white yellow NA male
4 IG-88 200 140 none metal red 15 none
5 Grega… 185 85 black dark brown NA <NA>
# ℹ 6 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>


Web https://tidydatatutor.com/ memungkinkan visualisasi operasi tidyverse (menggunakan pipe lama %>%)
Penting
Kamu harus selalu ingat untuk melakukan ungroup untuk menghapus variabel grup yang dibuat.
Versi “baru” dplyr sekarang memungkinkan menyertakan variabel grup dalam pemanggilan banyak fungsi dengan argumen by = ... atau .by = ....
# A tibble: 5 × 6
name height mass hair_color skin_color eye_color
<chr> <int> <dbl> <chr> <chr> <chr>
1 Yarael Poof 264 NA none white yellow
2 IG-88 200 140 none metal red
3 Taun We 213 NA none grey black
4 Jabba Desilijic Tiure 175 1358 <NA> green-tan, … orange
5 Gregar Typho 185 85 black dark brown
Opsi yang sangat berguna sebelum operasi adalah rowwise(): setiap operasi yang mengikutinya akan diterapkan pada setiap baris secara terpisah. Misalnya, mari definisikan dataset nilai fiktif.
Jika kita menerapkan rata-rata secara langsung, nilainya akan identik karena dihitung secara global, tetapi kita ingin mendapatkan rata-rata per catatan. Untuk itu gunakan rowwise().
Terakhir kita memiliki summarise(), yang memungkinkan mendapatkan ringkasan statistik. Misalnya, mari hitung rata-rata tinggi badan.
# A tibble: 1 × 1
ave_height
<dbl>
1 175.
Be careful
Perhatikan bahwa mutate() mengembalikan sebanyak baris seperti catatan asli, sementara summarise() menghitung dataset ringkasan baru, hanya menyertakan apa yang ditunjukkan.
Jika kita juga menggabungkan ini dengan pengelompokan dari group_by() atau .by = ..., dalam beberapa baris kode kamu bisa mendapatkan statistik yang dipecah.
Dalam dplyr baru terdapat reframe() untuk menghindari masalah summarise() ketika kita mengembalikan lebih dari satu nilai per variabel dalam ringkasan yang lebih kompleks.
Warning: Returning more (or less) than 1 row per `summarise()` group was
deprecated in dplyr 1.1.0.
ℹ Please use `reframe()` instead.
ℹ When switching from `summarise()` to `reframe()`, remember that
`reframe()` always returns an ungrouped data frame and adjust
accordingly.
# A tibble: 5 × 1
`quantile(mass)`
<dbl>
1 15
2 55.6
3 79
4 84.5
5 1358
Satu trik adalah memanfaatkan pemilih across() dan where(). Yang pertama memungkinkan kita bertindak pada beberapa kolom berdasarkan nama (dengan mutate() atau summarise()).
Warning: There was 1 warning in `summarise()`.
ℹ In argument: `ave = across(height:mass, mean, na.rm = TRUE)`.
ℹ In group 1: `sex = "male"`.
Caused by warning:
! The `...` argument of `across()` is deprecated as of dplyr 1.1.0.
Supply arguments directly to `.fns` through an anonymous function
instead.
# Previously
across(a:b, mean, na.rm = TRUE)
# Now
across(a:b, \(x) mean(x, na.rm = TRUE))
# A tibble: 5 × 2
sex ave$height $mass
<chr> <dbl> <dbl>
1 male 179. 80.2
2 none 131. 69.8
3 female 172. 54.7
4 hermaphroditic 175 1358
5 <NA> 175 81
Yang kedua, where(), memungkinkan hal yang sama tetapi memilih berdasarkan tipe.
# A tibble: 6 × 5
sex gender height mass birth_year
<chr> <chr> <dbl> <dbl> <dbl>
1 male masculine 179. 80.2 84.8
2 none masculine 140 69.8 53.3
3 female feminine 172. 54.7 47.2
4 hermaphroditic masculine 175 1358 600
5 <NA> <NA> 175 81 NaN
6 none feminine 96 NaN NaN
Coba kerjakan latihan-latihan berikut tanpa melihat solusinya
📝 Hitung berapa banyak karakter dari setiap spesies, diurutkan dari paling ke paling jarang.
📝 Setelah menghapus nilai hilang untuk berat dan tinggi, tambahkan variabel BMI dan tentukan rata-rata BMI karakter yang dipecah berdasarkan jenis kelamin.
📝 Dapatkan karakter termuda untuk setiap jenis kelamin.
📝 Dapatkan umur karakter termuda dan tertua dari setiap jenis kelamin.
📝 Tentukan jumlah karakter di setiap dekade (lihat round()), pertama tanpa dipecah lalu dipecah berdasarkan jenis kelamin.
Kita akan melakukan rangkuman apa yang dipelajari dalam tidyverse dengan tabel billboard dari paket tidyr. Dataset ini merepresentasikan sesuatu mirip top 40 (versi Amerika, top 100): untuk setiap artis dan lagu kita menyimpan tanggal saat masuk peringkat dan posisi yang ditempati di setiap minggu (wk1, wk2, …).
# A tibble: 317 × 8
artist track date.entered wk1 wk2 wk3 wk4 wk5
<chr> <chr> <date> <dbl> <dbl> <dbl> <dbl> <dbl>
1 2 Pac Baby Don… 2000-02-26 87 82 72 77 87
2 2Ge+her The Hard… 2000-09-02 91 87 92 NA NA
3 3 Doors Down Kryptoni… 2000-04-08 81 70 68 67 66
4 3 Doors Down Loser 2000-10-21 76 76 72 69 67
5 504 Boyz Wobble W… 2000-04-15 57 34 25 17 17
6 98^0 Give Me … 2000-08-19 51 39 34 26 26
7 A*Teens Dancing … 2000-07-08 97 97 96 95 100
8 Aaliyah I Don't … 2000-01-29 84 62 51 41 38
9 Aaliyah Try Again 2000-03-18 59 53 38 28 21
10 Adams, Yolanda Open My … 2000-08-26 76 76 74 69 68
# ℹ 307 more rows
Coba jawab pertanyaan-pertanyaan yang ada di workbook.
Mari terus berlatih dalam tidyverse dengan file futbol.csv, berisi data pemain dari 5 liga sepak bola pria utama, dari 2005 hingga 2019. Data diekstrak menggunakan paket worldfootballR dari https://www.fbref.com.
Rows: 40393 Columns: 16
── Column specification ──────────────────────────────────────────────
Delimiter: ","
chr (5): team, league, player, country, position
dbl (11): season, date_birth, minutes_playing, minutes_per_match_p...
ℹ Use `spec()` to retrieve the full column specification for this data.
ℹ Specify the column types or set `show_col_types = FALSE` to quiet this message.
# A tibble: 40,393 × 16
season team league player country position date_birth
<dbl> <chr> <chr> <chr> <chr> <chr> <dbl>
1 2005 Ajaccio Ligue 1 Djamel Abdoun ALG MF 1986
2 2005 Ajaccio Ligue 1 Gaspar Azevedo POR DF 1975
3 2005 Ajaccio Ligue 1 Yacine Bezzaz ALG MF 1981
4 2005 Ajaccio Ligue 1 Nicolas Bonnal FRA MF 1976
5 2005 Ajaccio Ligue 1 Marcelinho Cari… BRA MF 1971
6 2005 Ajaccio Ligue 1 Cyril Chapuis FRA FW 1979
7 2005 Ajaccio Ligue 1 Xavier Collin FRA DF 1974
8 2005 Ajaccio Ligue 1 Renaud Connen FRA MF 1980
9 2005 Ajaccio Ligue 1 Yohan Demont FRA DF,MF 1978
10 2005 Ajaccio Ligue 1 Christophe Dest… FRA DF 1973
# ℹ 40,383 more rows
# ℹ 9 more variables: minutes_playing <dbl>,
# minutes_per_match_playing <dbl>, goals <dbl>, assist <dbl>,
# goals_minus_pk <dbl>, pk <dbl>, pk_attemp <dbl>,
# yellow_card <dbl>, red_card <dbl>
Variabel-variabel mencatat informasi berikut:
season, team, league: musim, tim, dan liga.player, country, position, date_birth: nama, negara, posisi, dan tahun lahir pemain.minutes_playing, matches: total menit bermain dan pertandingan 90 menit.goals, assist: gol dan assist.pk, pk_attemp, goals_minus_pk: penalti, penalti yang dicoba, dan gol tanpa penalti.yellow_card, red_card: kartu kuning/merah.# A tibble: 40,393 × 16
season team league player country position date_birth
<dbl> <chr> <chr> <chr> <chr> <chr> <dbl>
1 2005 Ajaccio Ligue 1 Djamel Abdoun ALG MF 1986
2 2005 Ajaccio Ligue 1 Gaspar Azevedo POR DF 1975
3 2005 Ajaccio Ligue 1 Yacine Bezzaz ALG MF 1981
4 2005 Ajaccio Ligue 1 Nicolas Bonnal FRA MF 1976
5 2005 Ajaccio Ligue 1 Marcelinho Cari… BRA MF 1971
6 2005 Ajaccio Ligue 1 Cyril Chapuis FRA FW 1979
7 2005 Ajaccio Ligue 1 Xavier Collin FRA DF 1974
8 2005 Ajaccio Ligue 1 Renaud Connen FRA MF 1980
9 2005 Ajaccio Ligue 1 Yohan Demont FRA DF,MF 1978
10 2005 Ajaccio Ligue 1 Christophe Dest… FRA DF 1973
# ℹ 40,383 more rows
# ℹ 9 more variables: minutes_playing <dbl>,
# minutes_per_match_playing <dbl>, goals <dbl>, assist <dbl>,
# goals_minus_pk <dbl>, pk <dbl>, pk_attemp <dbl>,
# yellow_card <dbl>, red_card <dbl>
Coba jawab pertanyaan-pertanyaan yang ada di workbook.
Meskipun kita tidak dapat melakukan operasi aritmatika dengan mereka, beberapa operasi yang dapat kita lakukan dengan string teks akan penting. For that we will use the stringr package (within the same lubridate “universe of packages”).
Datasetnya adalah discursos (pidato, dari https://github.com/lirondos/discursos-de-navidad) yang menyimpan pidato Natal kepala negara Spanyol 1946–2021 (dalam kediktatoran dan demokrasi)
Coba jawab pertanyaan-pertanyaan yang ada di workbook.
Kembali ke R base: loop
Meskipun dalam banyak kasus dapat digantikan struktur yang lebih efisien dan mudah dibaca, penting mengetahui ekspresi kontrol paling terkenal: loop.
for { }: memungkinkan mengulang kode yang sama dalam jumlah tertentu dan diketahui kali.
while { }: memungkinkan mengulang kode yang sama dalam jumlah tidak ditentukan (sampai kondisi tidak lagi terpenuhi).
Loop for adalah struktur yang memungkinkan mengulang serangkaian perintah dalam jumlah terbatas, sudah ditentukan, dan diketahui berdasarkan sekumpulan indeks.
Mari definisikan vektor x <- c(0, -7, 1, 4) dan variabel kosong y. Kemudian kita mendefinisikan loop for dengan for () { }: di dalam tanda kurung kita menunjukkan indeks dan nilai-nilai yang akan dilalui, di dalam tanda kurung kurawal kode yang akan dieksekusi di setiap iterasi (dalam kasus ini, isi y sebagai x + 1).
Loop for adalah struktur yang memungkinkan mengulang serangkaian perintah dalam jumlah terbatas, sudah ditentukan, dan diketahui berdasarkan sekumpulan indeks.
Mari definisikan vektor x <- c(0, -7, 1, 4) dan variabel kosong y. Kemudian kita mendefinisikan loop for dengan for () { }: di dalam tanda kurung kita menunjukkan indeks dan nilai-nilai yang akan dilalui, di dalam tanda kurung kurawal kode yang akan dieksekusi di setiap iterasi (dalam kasus ini, isi y sebagai x + 1).
Loop for adalah struktur yang memungkinkan mengulang serangkaian perintah dalam jumlah terbatas, sudah ditentukan, dan diketahui berdasarkan sekumpulan indeks.
Mari definisikan vektor x <- c(0, -7, 1, 4) dan variabel kosong y. Kemudian kita mendefinisikan loop for dengan for () { }: di dalam tanda kurung kita menunjukkan indeks dan nilai-nilai yang akan dilalui, di dalam tanda kurung kurawal kode yang akan dieksekusi di setiap iterasi (dalam kasus ini, isi y sebagai x + 1).
Perhatikan bahwa karena R bekerja secara vektor default, loop ini sama dengan melakukan x + 1 secara langsung.
Opsi umum lainnya adalah menunjukkan indeks “secara otomatis”: dari yang pertama 1 hingga yang terakhir (sesuai panjang x length(x)).
Jadi struktur umum sebuah for-loop akan selalu sebagai berikut
Dalam kasus loop for kita SELALU mengetahui berapa banyak iterasi yang dilakukan (sebanyak elemen dalam set yang diindeks).
Seperti yang sudah kita pelajari dengan paket microbenchmark, kita dapat memeriksa bagaimana loop biasanya sangat tidak efisien (sehingga harus dihindari dalam sebagian besar kasus)
Kita dapat melihat contoh lain dari loop yang menggabungkan angka dan teks: kita mendefinisikan vektor umur dan nama, lalu mencetak nama dan umur ke-i.
Meskipun biasanya diindeks dengan vektor numerik, loop dapat diindeks pada struktur vektor apapun, terlepas dari tipe set-nya.
Mari gabungkan struktur kondisional dan loop: menggunakan set swiss dari paket {datasets}, mari tetapkan NA jika nilai kesuburan lebih dari 80.
Cara lain membuat loop adalah dengan struktur while { }, yang akan berulang dalam jumlah yang tidak diketahui, hingga kondisi tidak lagi terpenuhi (bahkan mungkin tidak pernah berakhir). Misalnya, kita menginisialisasi variabel times <- 1, ditambah setiap langkah, dan tidak keluar dari loop sampai times > 3.
Not yet, we are in the 1-th iteration
Not yet, we are in the 2-th iteration
Not yet, we are in the 3-th iteration
Now! We are in the 4-th iteration
A while loop will always look like this
Apa yang terjadi ketika kondisi tidak pernah FALSE? Coba sendiri
Peringatan
Loop while { } bisa cukup “berbahaya” jika kita tidak mengontrol dengan baik cara menghentikannya.
We have two reserved commands to abort a loop or force it forward:
break: allows abort a loop even if its end has not been reachedWe have two reserved commands to abort a loop or force it forward:
next: forces a loop to advance to the next iteration
Coba kerjakan latihan-latihan berikut tanpa melihat solusinya
📝 Modifikasi kode di bawah untuk mencetak pesan di layar jika dan hanya jika semua data dalam airquality adalah untuk bulan selain Januari.
📝 Modifikasi kode di bawah untuk menyimpan dalam variabel temp_high nilai TRUE jika ada catatan dengan suhu di atas 90°F dan FALSE dalam kasus lain.
📝 Modifikasi kode di bawah untuk merancang loop for dengan 5 iterasi yang melewati 5 bilangan ganjil pertama (dan mencetak setiap langkahnya).
Coba jawab pertanyaan-pertanyaan yang ada di workbook. On it you will have to design some simulation studies using conditional loops and structures.
Bayangkan kamu ada dalam kontes TV di mana diberikan pilihan 3 pintu: di salah satunya ada hadiah jutaan dan di 2 lainnya ada kue oreo.
Coba jawab pertanyaan-pertanyaan yang ada di workbook. On it you will have to design some simulation studies using conditional loops and structures.
Kembali ke R base: fungsi dan join
Kita tidak hanya dapat menggunakan fungsi bawaan yang sudah dimuat dalam paket, kita juga dapat membuat fungsi sendiri untuk mengotomatisasi tugas. Bagaimana cara membuat fungsi kita sendiri? Mari lihat skema dasarnya:
Kita tidak hanya dapat menggunakan fungsi bawaan yang sudah dimuat dalam paket, kita juga dapat membuat fungsi sendiri untuk mengotomatisasi tugas. Bagaimana cara membuat fungsi kita sendiri? Mari lihat skema dasarnya:
Kita tidak hanya dapat menggunakan fungsi bawaan yang sudah dimuat dalam paket, kita juga dapat membuat fungsi sendiri untuk mengotomatisasi tugas. Bagaimana cara membuat fungsi kita sendiri? Mari lihat skema dasarnya:
Kita tidak hanya dapat menggunakan fungsi bawaan yang sudah dimuat dalam paket, kita juga dapat membuat fungsi sendiri untuk mengotomatisasi tugas. Bagaimana cara membuat fungsi kita sendiri? Mari lihat skema dasarnya:
arg1, arg2, ...: adalah argumen input, argumen yang diterima fungsi untuk mengeksekusi kode di dalamnya.
code: baris kode yang ingin kita jalankan oleh fungsi.
return(var_output): argumen output akan dimasukkan.
Penting
Semua variabel yang kita definisikan di dalam fungsi adalah variabel LOKAL: hanya ada di dalam fungsi kecuali kita tentukan sebaliknya.
Mari lihat contoh sangat sederhana dari fungsi untuk menghitung luas persegi panjang.
Karena luas persegi panjang dihitung sebagai perkalian sisi-sisinya, kita hanya memerlukan sisi-sisinya: itulah argumen input dan nilai yang dikembalikan adalah luasnya (\(side_1 * side_2\)).
Mari lihat contoh sangat sederhana dari fungsi untuk menghitung luas persegi panjang.
Karena luas persegi panjang dihitung sebagai perkalian sisi-sisinya, kita hanya memerlukan sisi-sisinya: itulah argumen input dan nilai yang dikembalikan adalah luasnya (\(side_1 * side_2\)).
Mari lihat contoh sangat sederhana dari fungsi untuk menghitung luas persegi panjang.
Karena luas persegi panjang dihitung sebagai perkalian sisi-sisinya, kita hanya memerlukan sisi-sisinya: itulah argumen input dan nilai yang dikembalikan adalah luasnya (\(side_1 * side_2\)).
Kita juga dapat membuat definisi variabel secara langsung tanpa menyimpan di tengah jalan.
Tip
Meskipun tidak wajib, disarankan membuat pemanggilan argumen secara eksplisit, menentukan nilai untuk setiap argumen agar tidak bergantung pada urutannya, membuat kode lebih mudah dibaca.
Bayangkan kita menyadari bahwa 90% waktu kita menggunakan fungsi tersebut untuk menghitung luas persegi secara default (yaitu, hanya butuh satu sisi). Untuk itu, kita dapat mendefinisikan argumen default dalam fungsi: argumen akan mengambil nilai tersebut kecuali kita tetapkan nilai lain.
Mengapa tidak menetapkan side_2 = side_1 secara default, untuk menghemat baris kode dan waktu?
Sekarang secara default sisi kedua akan sama dengan sisi pertama (jika ditambahkan akan menggunakan keduanya).
Mari perumit fungsi sedikit dan tambahkan dalam output nilai setiap sisi, berlabel side_1 dan side_2, mengemas output dalam sebuah vektor.
Kita dapat memperumit output sedikit lagi dengan menambahkan variabel keempat yang memberi tahu kita, bergantung pada argumen, apakah persegi panjang atau persegi, dengan menambahkan variabel karakter (atau logika) dalam output.
area side_1 side_2 type
"15" "5" "3" "rectangle"
Masalah: saat mencoba menggabungkan angka dan teks, semuanya dikonversi menjadi angka. Kita bisa menyimpan semuanya dalam tibble() atau dalam objek yang dikenal di R sebagai list (akan kita lihat nanti).
Sebelumnya kita tidak peduli dengan urutan argumen, tetapi sekarang urutan argumen input penting, karena kita menyertakan side_1 dan side_2 dalam output.
Tampaknya sepele apa yang kita lakukan tetapi kita telah melewati batas penting: beralih dari mengonsumsi pengetahuan (kode dari paket orang lain), ke menghasilkan pengetahuan dengan membuat fungsi kita sendiri.
Fungsi akan menjadi kunci dalam pekerjaan sehari-hari karena memungkinkan kamu mengotomatisasi kode yang akan diulang berkali-kali: dengan mengemas kode tersebut di bawah alias (nama fungsi) kamu akan dapat menggunakannya berulang kali tanpa harus memrogramnya lagi
Aspek penting tentang fungsi: apa yang terjadi jika kita menamai variabel di dalam fungsi yang lupa kita tetapkan nilainya di dalam fungsi.
Kita harus berhati-hati saat menggunakan fungsi di R, karena berdasarkan “aturan leksikografi”, jika variabel tidak didefinisikan di dalam fungsi, R akan mencari variabel tersebut di lingkungan variabel.
Jika variabel sudah didefinisikan di luar fungsi (lingkungan global), dan juga digunakan di dalam untuk mengubah nilainya, nilai tersebut hanya berubah di dalam tetapi tidak di lingkungan global.
Jika kita ingin itu berubah secara lokal maupun global kita harus menggunakan penugasan ganda (<<-).
Coba kerjakan latihan-latihan berikut tanpa melihat solusinya
📝 Modifikasi kode di bawah untuk mendefinisikan fungsi bernama sum_function, yang diberikan dua elemen mengembalikan jumlahnya.
📝 Modifikasi kode di bawah untuk mendefinisikan fungsi product_function, yang diberikan dua elemen mengembalikan perkaliannya, tetapi secara default menghitung kuadrat.
📝 Definisikan fungsi equal_names yang, diberikan dua nama, memberi tahu apakah sama atau tidak. Lakukan ini dengan mempertimbangkan case-sensitive dan case-insensitive menggunakan paket stringr.
# Case-sensitive
equal_names <- function(person_1, person_2) {
return(person_1 == person_2)
}
equal_names("Javi", "javi")
equal_names("Javi", "Lucía")
# Case-insensitive
library(stringr)
equal_names <- function(person_1, person_2) {
return(str_equal(person_1, person_2, ignore_case = TRUE))
# other option
# return(str_to_lower(person_1) == str_to_lower(person_2))
# other option
# return(str_to_upper(person_1) == str_to_upper(person_2))
}
equal_names("Javi", "javi")
equal_names("Javi", "Lucía")📝 Buat fungsi compute_BMI yang, diberikan berat, tinggi (meter), dan nama, mengembalikan list dengan BMI (\(weight/(height^2)\)) dan nama.
📝 Ulangi latihan sebelumnya dengan argumen opsional tambahan units (default units = "meters"). Kembangkan fungsi agar benar untuk units = "meters" dan units = "centimeters".
📝 Buat tibble fiktif 7 orang, dengan tiga variabel (nama karangan, berat dan tinggi simulasi dalam cm), dan terapkan fungsi agar mendapatkan kolom keempat berisi BMI.
📝 Buat fungsi shortcut dengan dua argumen numerik x dan y. Jika keduanya sama, kembalikan equal dan fungsi berhenti. PERINGATAN: x dan y bisa berupa vektor. Jika berbeda (panjang sama) hitung proporsi elemen yang berbeda. Jika berbeda (panjang berbeda), kembalikan elemen yang tidak sama.
Untuk berlatih dengan fungsi kita akan membuat konverter suhu lengkap yang, diberikan suhu dalam Fahrenheit, Celsius, atau Kelvin, mengonversinya ke salah satu yang lain.
Coba jawab pertanyaan-pertanyaan yang ada di workbook
Saat bekerja dengan data kita tidak selalu memiliki informasi dalam satu tabel, dan terkadang kita tertarik untuk mereferensikan silang informasi dari sumber yang berbeda.
inner_join(): hanya catatan dengan id di kedua tabel yang bertahan.
full_join(): menyimpan semua catatan di kedua tabel.
left_join(): menyimpan semua catatan dari tabel pertama, dan mencari yang juga memiliki id di tabel kedua (jika tidak ada, diisi dengan NA pada field tabel ke-2).
right_join(): menyimpan semua catatan di tabel kedua, dan mencari yang juga memiliki id di tabel pertama.
Mari uji berbagai join dengan contoh sederhana
Bayangkan kita ingin memasukkan ke tb_1 informasi dari tabel_2, mengidentifikasi catatan berdasarkan kolom kunci (by = "key"): kita ingin menyimpan semua catatan tabel pertama dan mencari yang memiliki nilai sama dalam key juga di tabel kedua.
# A tibble: 3 × 3
key val_x val_y
<dbl> <chr> <chr>
1 1 x1 y1
2 2 x2 y2
3 3 x3 <NA>
Perhatikan bahwa catatan di tabel pertama yang kuncinya tidak ditemukan di tabel kedua diberi nilai hilang (NA).
Operasi right_join() adalah kebalikannya: kita sekarang akan memasukkan ke tb_2 informasi dari tabel lain, mengidentifikasi catatan berdasarkan kolom key: kita ingin menyimpan semua catatan tabel kedua dan mencari yang memiliki nilai sama dalam key juga di tabel pertama.
# A tibble: 3 × 3
key val_x val_y
<dbl> <chr> <chr>
1 1 x1 y1
2 2 x2 y2
3 4 <NA> y3
Perhatikan bahwa sekarang catatan di tabel kedua yang kuncinya tidak ditemukan di tabel pertama yang diberi nilai hilang (NA).
Kolom kunci yang akan kita gunakan untuk penggabungan tidak selalu diberi nama yang sama.
by = c("key_2" = "key_2"): kita menunjukkan di kolom mana dari setiap tabel terdapat kunci yang akan digabungkan.Kita juga dapat menggabungkan beberapa kolom sekaligus (akan menginterpretasikan catatan yang sama sebagai yang memiliki set kunci yang sama), dengan by = c("var1_t1" = "var1_t2", "var2_t1" = "var2_t2", ...).
Bisa juga terjadi bahwa saat menggabungkan dua tabel, terdapat kolom nilai yang diberi nama sama
Sufiks ini dapat ditentukan dalam argumen opsional suffix = ..., yang memungkinkan kita membedakan variabel dari satu tabel dengan tabel lainnya.
Dua kasus sebelumnya membentuk yang dikenal sebagai outer join: penggabungan di mana pengamatan yang muncul di setidaknya satu tabel disimpan. Outer join ketiga adalah full_join() yang akan menyimpan pengamatan dari kedua tabel, menambahkan baris yang tidak cocok dengan tabel lain.
Berlawanan dengan outer join adalah yang dikenal sebagai inner join, dengan inner_join(): penggabungan di mana hanya pengamatan yang muncul di kedua tabel yang disimpan.
Perhatikan bahwa dalam hal catatan, inner_join bersifat komutatif, kita tidak peduli dengan urutan tabel: satu-satunya yang berubah adalah urutan kolom yang ditambahkan.
Terakhir kita memiliki dua alat menarik untuk memfilter (bukan menggabungkan) catatan: semi_join() dan anti_join(). Semi join menyisakan di tabel pertama catatan yang kuncinya juga ada di tabel kedua (seperti inner join tanpa menambahkan info dari tabel kedua). Anti join melakukan sebaliknya.
Untuk latihan kita akan menggunakan tabel dari paket nycflights13.
📝 Dari paket nycflights13 gabungkan data maskapai dari airlines ke tabel flights. Pertahankan semua catatan penerbangan.
📝 Ke tabel dari bagian sebelumnya, tambahkan data pesawat dari planes, hanya untuk penerbangan yang kita miliki informasi pesawatnya.
📝 Ulangi latihan sebelumnya tetapi simpan kedua variabel year (tahun penerbangan dan tahun pembuatan pesawat), dan bedakan keduanya.
📝 Tambahkan bujur dan lintang bandara dari airports, bedakan antara bandara tujuan dan asal.
📝 Filter dari airports hanya bandara tempat penerbangan berangkat. Ulangi untuk bandara tujuan.
Kita akan berlatih join sederhana menggunakan dataset band_members dan band_instruments yang sudah ada dalam paket dplyr.
# A tibble: 3 × 2
name band
<chr> <chr>
1 Mick Stones
2 John Beatles
3 Paul Beatles
# A tibble: 3 × 2
name plays
<chr> <chr>
1 John guitar
2 Paul bass
3 Keith guitar
Coba jawab pertanyaan-pertanyaan yang ada di workbook
Dalam file municipios.csv kita menyimpan informasi tentang kotamadya Spanyol per tahun 2019.
Variabel LAU_code mewakili kode sebagai unit administratif lokal di UE (lihat lebih lanjut di https://ec.europa.eu/eurostat/web/nuts/local-administrative-units).
Variabel codigo_ine dibentuk dengan menggabungkan kode provinsi dan kode komunitas (setiap provinsi memiliki kode dari 1 hingga 52, tidak bergantung pada ccaa).
Rows: 8212 Columns: 8
── Column specification ──────────────────────────────────────────────
Delimiter: ","
chr (8): codauto, ine.ccaa.name, cpro, ine.prov.name, cmun, name, ...
ℹ Use `spec()` to retrieve the full column specification for this data.
ℹ Specify the column types or set `show_col_types = FALSE` to quiet this message.
# A tibble: 8,212 × 8
codauto ine.ccaa.name cpro ine.prov.name cmun name LAU_CODE
<chr> <chr> <chr> <chr> <chr> <chr> <chr>
1 01 Andalucía 04 Almería 001 Abla 04001
2 01 Andalucía 04 Almería 002 Abrucena 04002
3 01 Andalucía 04 Almería 003 Adra 04003
4 01 Andalucía 04 Almería 004 Albanchez 04004
5 01 Andalucía 04 Almería 005 Alboloduy 04005
6 01 Andalucía 04 Almería 006 Albox 04006
7 01 Andalucía 04 Almería 007 Alcolea 04007
8 01 Andalucía 04 Almería 008 Alcóntar 04008
9 01 Andalucía 04 Almería 009 Alcudia d… 04009
10 01 Andalucía 04 Almería 010 Alhabia 04010
# ℹ 8,202 more rows
# ℹ 1 more variable: codigo_ine <chr>
Di sisi lain, dalam file renta_mun kita memiliki pendapatan per kapita rata-rata setiap unit administratif (kotamadya, distrik, provinsi, komunitas otonom,…) untuk berbagai tahun.
Warning: One or more parsing issues, call `problems()` on your data frame for
details, e.g.:
dat <- vroom(...)
problems(dat)
Rows: 55273 Columns: 7
── Column specification ──────────────────────────────────────────────
Delimiter: ","
chr (2): Unidad, codigo_ine
dbl (5): 2019, 2018, 2017, 2016, 2015
ℹ Use `spec()` to retrieve the full column specification for this data.
ℹ Specify the column types or set `show_col_types = FALSE` to quiet this message.
# A tibble: 55,273 × 7
Unidad `2019` `2018` `2017` `2016` `2015` codigo_ine
<chr> <dbl> <dbl> <dbl> <dbl> <dbl> <chr>
1 44001 Ababuj NA NA NA NA NA 44001
2 4400101 Ababuj distr… NA NA NA NA NA 4400101
3 4400101001 Ababuj se… NA NA NA NA NA 4400101001
4 40001 Abades 11429 10731 10314 9816 9904 40001
5 4000101 Abades distr… 11429 10731 10314 9816 9904 4000101
6 4000101001 Abades se… 11429 10731 10314 9816 9904 4000101001
7 10001 Abadía 8954 8589 8207 7671 8416 10001
8 1000101 Abadía distr… 8954 8589 8207 7671 8416 1000101
9 1000101001 Abadía se… 8954 8589 8207 7671 8416 1000101001
10 27001 Abadín 10791 10258 9762 9478 9116 27001
# ℹ 55,263 more rows
Sebelum memulai mari kita normalisasi nama variabel menggunakan clean_names() dari paket janitor.
Coba jawab pertanyaan-pertanyaan yang ada di workbook
Impor dan ekspor data
Sejauh ini kita hanya menggunakan data yang sudah dimuat dalam paket tetapi sering kali kita perlu mengimpor data dari luar. Salah satu kekuatan utama R adalah kita dapat mengimpor data dengan sangat mudah dalam berbagai format:
R native formats: .rda, .RData and .rds formats.
Rectangular (tabular) data: .csv and .tsv formats
Untabulated data: .txt format.
Data in excel: .xls and .xlsx formats
Data from SAS/Stata/SPSS: .sas7bdat, .sav and .dat formats
Data from Google Drive
Data from API’s: aemet, catastro, twitter, spotify, etc.
File paling sederhana untuk diimpor ke R (dan biasanya membutuhkan lebih sedikit ruang disk) adalah ekstensi aslinya: file dalam format .RData, .rda, dan .rds. Untuk memuat yang pertama cukup gunakan fungsi native load() dengan memberikan path file.
RData: kita akan mengimpor file world_bank_pop.RData, yang menyertakan dataset world_bank_pop
# A tibble: 1,064 × 20
country indicator `2000` `2001` `2002` `2003` `2004` `2005`
<chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
1 ABW SP.URB.TOTL 4.16e4 4.20e+4 4.22e+4 4.23e+4 4.23e+4 4.24e+4
2 ABW SP.URB.GROW 1.66e0 9.56e-1 4.01e-1 1.97e-1 9.46e-2 1.94e-1
3 ABW SP.POP.TOTL 8.91e4 9.07e+4 9.18e+4 9.27e+4 9.35e+4 9.45e+4
4 ABW SP.POP.GROW 2.54e0 1.77e+0 1.19e+0 9.97e-1 9.01e-1 1.00e+0
5 AFE SP.URB.TOTL 1.16e8 1.20e+8 1.24e+8 1.29e+8 1.34e+8 1.39e+8
6 AFE SP.URB.GROW 3.60e0 3.66e+0 3.72e+0 3.71e+0 3.74e+0 3.81e+0
7 AFE SP.POP.TOTL 4.02e8 4.12e+8 4.23e+8 4.34e+8 4.45e+8 4.57e+8
8 AFE SP.POP.GROW 2.58e0 2.59e+0 2.61e+0 2.62e+0 2.64e+0 2.67e+0
9 AFG SP.URB.TOTL 4.31e6 4.36e+6 4.67e+6 5.06e+6 5.30e+6 5.54e+6
10 AFG SP.URB.GROW 1.86e0 1.15e+0 6.86e+0 7.95e+0 4.59e+0 4.47e+0
# ℹ 1,054 more rows
# ℹ 12 more variables: `2006` <dbl>, `2007` <dbl>, `2008` <dbl>,
# `2009` <dbl>, `2010` <dbl>, `2011` <dbl>, `2012` <dbl>,
# `2013` <dbl>, `2014` <dbl>, `2015` <dbl>, `2016` <dbl>,
# `2017` <dbl>
.rda: kita akan mengimpor dataset airquality dari airquality.rda
# A tibble: 153 × 6
Ozone Solar.R Wind Temp Month Day
<int> <int> <dbl> <int> <int> <int>
1 41 190 7.4 67 5 1
2 36 118 8 72 5 2
3 12 149 12.6 74 5 3
4 18 313 11.5 62 5 4
5 NA NA 14.3 56 5 5
6 28 NA 14.9 66 5 6
7 23 299 8.6 65 5 7
8 19 99 13.8 59 5 8
9 8 19 20.1 61 5 9
10 NA 194 8.6 69 5 10
# ℹ 143 more rows
Perhatikan bahwa file yang dimuat dengan load() secara otomatis dimuat ke dalam lingkungan (dengan nama yang aslinya disimpan), dan bukan hanya dataset yang dapat dimuat: load() memungkinkan kita memuat beberapa objek (bukan hanya data tabular)
File .rda dan .RData native adalah cara yang tepat untuk menyimpan lingkungan kerjamu.
.rds: untuk tipe ini kita harus menggunakan readRDS(), dan perlu menyertakan argumen file dengan path. Dalam kasus ini kita akan mengimpor data kanker paru dari North Central Cancer Treatment Group. Perhatikan bahwa file impor .rds adalah satu database
# A tibble: 228 × 10
inst time status age sex ph.ecog ph.karno pat.karno meal.cal
<dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
1 3 306 2 74 1 1 90 100 1175
2 3 455 2 68 1 0 90 90 1225
3 3 1010 1 56 1 0 90 90 NA
4 5 210 2 57 1 1 90 60 1150
5 1 883 2 60 1 0 100 90 NA
6 12 1022 1 74 1 1 50 80 513
7 7 310 2 68 2 2 70 60 384
8 11 361 2 71 2 2 60 80 538
9 1 218 2 53 1 1 70 80 825
10 7 166 2 61 1 2 70 70 271
# ℹ 218 more rows
# ℹ 1 more variable: wt.loss <dbl>
Penting
The paths must always be without spaces, ñ, or accents.
Paket readr dalam lingkungan tidyverse berisi beberapa fungsi berguna untuk memuat data persegi panjang (tanpa pemformatan).
read_csv(): .csv files whose separator is comma
read_csv2(): semicolon
read_tsv(): tabulator.read_table(): space.read_delim(): generic function for character delimited files.
Semuanya membutuhkan argumen path file ditambah argumen opsional (lewati header atau tidak, desimal, dll). Lihat lebih lanjut di https://readr.tidyverse.org/
Keunggulan utama readr adalah mengotomatisasi pemformatan untuk beralih dari file datar (tidak terformat) ke tibble (dalam baris dan kolom, dengan pemformatan).
.csv: dengan read_csv() kita akan memuat file dipisahkan koma, memberikan argumen path di file = .... Mari impor dataset chickens.csv. Output-nya memberi kita tipe variabel.Rows: 5 Columns: 4
── Column specification ──────────────────────────────────────────────
Delimiter: ","
chr (3): chicken, sex, motto
dbl (1): eggs_laid
ℹ Use `spec()` to retrieve the full column specification for this data.
ℹ Specify the column types or set `show_col_types = FALSE` to quiet this message.
# A tibble: 5 × 4
chicken sex eggs_laid motto
<chr> <chr> <dbl> <chr>
1 Foghorn Leghorn rooster 0 That's a joke, ah say, th…
2 Chicken Little hen 3 The sky is falling!
3 Ginger hen 12 Listen. We'll either die …
4 Camilla the Chicken hen 7 Bawk, buck, ba-gawk.
5 Ernie The Giant Chicken rooster 0 Put Captain Solo in the c…
Format variabel biasanya dilakukan secara otomatis oleh read_csv(), dan kita dapat memeriksanya dengan spec().
Meskipun biasanya dilakukan dengan baik secara otomatis, kita dapat menentukan format secara eksplisit dalam col_types = list() (dalam format list, dengan col_xxx() untuk setiap tipe variabel).
# A tibble: 5 × 4
chicken sex eggs_laid motto
<chr> <chr> <chr> <chr>
1 Foghorn Leghorn rooster 0 That's a joke, ah say, th…
2 Chicken Little hen 3 The sky is falling!
3 Ginger hen 12 Listen. We'll either die …
4 Camilla the Chicken hen 7 Bawk, buck, ba-gawk.
5 Ernie The Giant Chicken rooster 0 Put Captain Solo in the c…
Kita bahkan dapat menunjukkan variabel yang ingin dipilih (tanpa menghabiskan memori), dengan menunjukkannya dalam col_select = ....
Rows: 5 Columns: 3
── Column specification ──────────────────────────────────────────────
Delimiter: ","
chr (2): chicken, sex
dbl (1): eggs_laid
ℹ Use `spec()` to retrieve the full column specification for this data.
ℹ Specify the column types or set `show_col_types = FALSE` to quiet this message.
# A tibble: 5 × 3
chicken sex eggs_laid
<chr> <chr> <dbl>
1 Foghorn Leghorn rooster 0
2 Chicken Little hen 3
3 Ginger hen 12
4 Camilla the Chicken hen 7
5 Ernie The Giant Chicken rooster 0
Apa yang terjadi ketika pemisah tidak benar?
Jika menggunakan read_csv() diharapkan pemisah antar kolom adalah koma, tetapi seperti yang terlihat dengan .txt berikut, semuanya diinterpretasikan sebagai satu kolom: tidak ada koma dan tidak tahu di mana harus memisahkan
Rows: 10 Columns: 1
── Column specification ──────────────────────────────────────────────
Delimiter: ","
chr (1): UCC PAY LAZ KPK RT COF BIH DII ENG ACU Rank Team ...
ℹ Use `spec()` to retrieve the full column specification for this data.
ℹ Specify the column types or set `show_col_types = FALSE` to quiet this message.
[1] 10 1
# A tibble: 10 × 1
UCC PAY LAZ KPK RT COF BIH DII ENG ACU Rank Team Co…¹
<chr>
1 1 1 1 1 1 1 1 1 1 1 1 Ohio St B10
2 2 2 2 2 2 2 2 2 4 2 2 Oregon P12
3 3 4 3 4 3 4 3 4 2 3 3 Alabama SEC
4 4 3 4 3 4 3 5 3 3 4 4 TCU B12
5 6 6 6 5 5 7 6 5 6 11 5 Michigan St B10
6 7 7 7 6 7 6 11 8 7 8 6 Georgia SEC
7 5 5 5 7 6 8 4 6 5 5 7 Florida St ACC
8 8 8 9 9 10 5 7 7 10 7 8 Baylor B12
9 9 11 8 13 11 11 12 9 14 9 9 Georgia Tech ACC
10 13 10 13 11 8 9 10 11 9 10 10 Mississippi SEC
# ℹ abbreviated name:
# ¹`UCC PAY LAZ KPK RT COF BIH DII ENG ACU Rank Team Conf`
Untuk itu kita memiliki:
read_csv2() ketika pemisah adalah titik koma, read_tsv() ketika tabulasi, dan read_table() ketika spasi.
read_delim() in general.
── Column specification ──────────────────────────────────────────────
cols(
UCC = col_double(),
PAY = col_double(),
LAZ = col_double(),
KPK = col_double(),
RT = col_double(),
COF = col_double(),
BIH = col_double(),
DII = col_double(),
ENG = col_double(),
ACU = col_double(),
Rank = col_double(),
Team = col_character(),
Conf = col_character()
)
Warning: 10 parsing failures.
row col expected actual file
1 -- 13 columns 15 columns './data/massey-rating.txt'
2 -- 13 columns 14 columns './data/massey-rating.txt'
3 -- 13 columns 14 columns './data/massey-rating.txt'
4 -- 13 columns 14 columns './data/massey-rating.txt'
5 -- 13 columns 15 columns './data/massey-rating.txt'
... ... .......... .......... ..........................
See problems(...) for more details.
# A tibble: 10 × 13
UCC PAY LAZ KPK RT COF BIH DII ENG ACU Rank
<dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
1 1 1 1 1 1 1 1 1 1 1 1
2 2 2 2 2 2 2 2 2 4 2 2
3 3 4 3 4 3 4 3 4 2 3 3
4 4 3 4 3 4 3 5 3 3 4 4
5 6 6 6 5 5 7 6 5 6 11 5
6 7 7 7 6 7 6 11 8 7 8 6
7 5 5 5 7 6 8 4 6 5 5 7
8 8 8 9 9 10 5 7 7 10 7 8
9 9 11 8 13 11 11 12 9 14 9 9
10 13 10 13 11 8 9 10 11 9 10 10
# ℹ 2 more variables: Team <chr>, Conf <chr>
Paket impor kunci lainnya adalah readxl untuk mengimpor data dari Excel. Tiga fungsi yang menjadi kunci:
read_xls() specific to .xls, read_xlsx() specific to .xlsx.read_excel(): for both .xls and .xlsx.Kita akan mengimpor deaths.xlsx dengan catatan kematian selebriti.
New names:
• `` -> `...2`
• `` -> `...3`
• `` -> `...4`
• `` -> `...5`
• `` -> `...6`
# A tibble: 18 × 6
`Lots of people` ...2 ...3 ...4 ...5 ...6
<chr> <chr> <chr> <chr> <chr> <chr>
1 simply cannot resist writing <NA> <NA> <NA> <NA> some…
2 at the top <NA> of thei…
3 or merging <NA> <NA> <NA> cells
4 Name Profession Age Has … Date… Date…
5 David Bowie musician 69 TRUE 17175 42379
6 Carrie Fisher actor 60 TRUE 20749 42731
7 Chuck Berry musician 90 TRUE 9788 42812
8 Bill Paxton actor 61 TRUE 20226 42791
9 Prince musician 57 TRUE 21343 42481
10 Alan Rickman actor 69 FALSE 16854 42383
11 Florence Henderson actor 82 TRUE 12464 42698
12 Harper Lee author 89 FALSE 9615 42419
13 Zsa Zsa Gábor actor 99 TRUE 6247 42722
14 George Michael musician 53 FALSE 23187 42729
15 Some <NA> <NA> <NA> <NA> <NA>
16 <NA> also like to … <NA> <NA> <NA> <NA>
17 <NA> <NA> at t… bott… <NA> <NA>
18 <NA> <NA> <NA> <NA> <NA> too!
# A tibble: 6 × 6
`Lots of people` ...2 ...3 ...4 ...5 ...6
<chr> <chr> <chr> <chr> <chr> <chr>
1 simply cannot resist writing <NA> <NA> <NA> <NA> some…
2 at the top <NA> of thei…
3 or merging <NA> <NA> <NA> cells
4 Name Profession Age Has kids Date o… Date…
5 David Bowie musician 69 TRUE 17175 42379
6 Carrie Fisher actor 60 TRUE 20749 42731
Satu hal yang sangat umum terjadi adalah ada semacam komentar atau teks di awal file, sehingga harus melewati baris-baris tersebut.
Kita dapat melewati baris-baris ini langsung saat memuat dengan skip = ... (menunjukkan jumlah baris yang akan dilewati).
# A tibble: 14 × 6
Name Profession Age `Has kids` `Date of birth`
<chr> <chr> <chr> <chr> <dttm>
1 David Bowie musician 69 TRUE 1947-01-08 00:00:00
2 Carrie Fisher actor 60 TRUE 1956-10-21 00:00:00
3 Chuck Berry musician 90 TRUE 1926-10-18 00:00:00
4 Bill Paxton actor 61 TRUE 1955-05-17 00:00:00
5 Prince musician 57 TRUE 1958-06-07 00:00:00
6 Alan Rickman actor 69 FALSE 1946-02-21 00:00:00
7 Florence Henderson actor 82 TRUE 1934-02-14 00:00:00
8 Harper Lee author 89 FALSE 1926-04-28 00:00:00
9 Zsa Zsa Gábor actor 99 TRUE 1917-02-06 00:00:00
10 George Michael musician 53 FALSE 1963-06-25 00:00:00
11 Some <NA> <NA> <NA> NA
12 <NA> also like … <NA> <NA> NA
13 <NA> <NA> at t… bottom, NA
14 <NA> <NA> <NA> <NA> NA
# ℹ 1 more variable: `Date of death` <chr>
Selain itu dengan col_names = ... kita sudah dapat mengganti nama kolom saat impor (jika menyediakan nama berarti baris pertama sudah dianggap sebagai data)
# A tibble: 14 × 6
name profession age kids birth death
<chr> <chr> <chr> <chr> <dttm> <chr>
1 David Bowie musician 69 TRUE 1947-01-08 00:00:00 42379
2 Carrie Fisher actor 60 TRUE 1956-10-21 00:00:00 42731
3 Chuck Berry musician 90 TRUE 1926-10-18 00:00:00 42812
4 Bill Paxton actor 61 TRUE 1955-05-17 00:00:00 42791
5 Prince musician 57 TRUE 1958-06-07 00:00:00 42481
6 Alan Rickman actor 69 FALSE 1946-02-21 00:00:00 42383
7 Florence Henderson actor 82 TRUE 1934-02-14 00:00:00 42698
8 Harper Lee author 89 FALSE 1926-04-28 00:00:00 42419
9 Zsa Zsa Gábor actor 99 TRUE 1917-02-06 00:00:00 42722
10 George Michael musician 53 FALSE 1963-06-25 00:00:00 42729
11 Some <NA> <NA> <NA> NA <NA>
12 <NA> also like… <NA> <NA> NA <NA>
13 <NA> <NA> at t… bott… NA <NA>
14 <NA> <NA> <NA> <NA> NA too!
Terkadang tanggal Excel diformat secara tidak benar (mengejutkan): kita dapat menggunakan convertToDate() dari paket openxlsx untuk mengonversinya.
Warning in convertToDate(deaths$death): NAs introduced by coercion
# A tibble: 14 × 6
name profession age kids birth death
<chr> <chr> <chr> <chr> <dttm> <date>
1 David Bowie musician 69 TRUE 1947-01-08 00:00:00 2016-01-10
2 Carrie Fisher actor 60 TRUE 1956-10-21 00:00:00 2016-12-27
3 Chuck Berry musician 90 TRUE 1926-10-18 00:00:00 2017-03-18
4 Bill Paxton actor 61 TRUE 1955-05-17 00:00:00 2017-02-25
5 Prince musician 57 TRUE 1958-06-07 00:00:00 2016-04-21
6 Alan Rickman actor 69 FALSE 1946-02-21 00:00:00 2016-01-14
7 Florence Hen… actor 82 TRUE 1934-02-14 00:00:00 2016-11-24
8 Harper Lee author 89 FALSE 1926-04-28 00:00:00 2016-02-19
9 Zsa Zsa Gábor actor 99 TRUE 1917-02-06 00:00:00 2016-12-18
10 George Micha… musician 53 FALSE 1963-06-25 00:00:00 2016-12-25
11 Some <NA> <NA> <NA> NA NA
12 <NA> also like… <NA> <NA> NA NA
13 <NA> <NA> at t… bott… NA NA
14 <NA> <NA> <NA> <NA> NA NA
Kita juga dapat memuat Excel dengan beberapa sheet: untuk menunjukkan sheet (berdasarkan nama atau nomor) gunakan argumen sheet = ....
# A tibble: 32 × 11
mpg cyl disp hp drat wt qsec vs am gear carb
<dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
1 21 6 160 110 3.9 2.62 16.5 0 1 4 4
2 21 6 160 110 3.9 2.88 17.0 0 1 4 4
3 22.8 4 108 93 3.85 2.32 18.6 1 1 4 1
4 21.4 6 258 110 3.08 3.22 19.4 1 0 3 1
5 18.7 8 360 175 3.15 3.44 17.0 0 0 3 2
6 18.1 6 225 105 2.76 3.46 20.2 1 0 3 1
7 14.3 8 360 245 3.21 3.57 15.8 0 0 3 4
8 24.4 4 147. 62 3.69 3.19 20 1 0 4 2
9 22.8 4 141. 95 3.92 3.15 22.9 1 0 4 2
10 19.2 6 168. 123 3.92 3.44 18.3 1 0 4 4
# ℹ 22 more rows
Kita bahkan dapat menunjukkan rentang sel yang akan dimuat dengan range = ....
Paket haven dalam orbit tidyverse memungkinkan kita mengimpor file dari 3 perangkat lunak komersial terpenting: SAS, SPSS, dan Stata.
Dengan cara yang sama seperti kita dapat mengimpor, kita juga dapat mengekspor
.RData (opsi yang disarankan untuk variabel yang disimpan di R). Ingat ekstensi ini hanya dapat digunakan di R. Gunakan saja save(object, file = path).Dengan cara yang sama seperti kita dapat mengimpor, kita juga dapat mengekspor
.RData multiple objectsDengan cara yang sama seperti kita dapat mengimpor, kita juga dapat mengekspor
.csv. Gunakan saja write_csv(object, file = path).Rows: 4 Columns: 2
── Column specification ──────────────────────────────────────────────
Delimiter: ","
dbl (2): a, b
ℹ Use `spec()` to retrieve the full column specification for this data.
ℹ Specify the column types or set `show_col_types = FALSE` to quiet this message.
# A tibble: 4 × 2
a b
<dbl> <dbl>
1 1 1
2 2 2
3 3 3
4 4 4
Salah satu keunggulan utama R adalah kita dapat menggunakan fungsi impor langsung dari web, tanpa mengunduh secara manual: cukup berikan tautan sebagai pengganti path lokal. Misalnya, kita akan mengunduh data covid dari ISCIII (https://cnecovid.isciii.es/covid19/#documentaci%C3%B3n-y-datos)
Rows: 500 Columns: 8
── Column specification ──────────────────────────────────────────────
Delimiter: ","
chr (3): provincia_iso, sexo, grupo_edad
dbl (4): num_casos, num_hosp, num_uci, num_def
date (1): fecha
ℹ Use `spec()` to retrieve the full column specification for this data.
ℹ Specify the column types or set `show_col_types = FALSE` to quiet this message.
# A tibble: 500 × 8
provincia_iso sexo grupo_edad fecha num_casos num_hosp
<chr> <chr> <chr> <date> <dbl> <dbl>
1 A H 0-9 2020-01-01 0 0
2 A H 10-19 2020-01-01 0 0
3 A H 20-29 2020-01-01 0 0
4 A H 30-39 2020-01-01 0 0
5 A H 40-49 2020-01-01 0 0
6 A H 50-59 2020-01-01 0 0
7 A H 60-69 2020-01-01 0 0
8 A H 70-79 2020-01-01 0 0
9 A H 80+ 2020-01-01 0 0
10 A H NC 2020-01-01 0 0
# ℹ 490 more rows
# ℹ 2 more variables: num_uci <dbl>, num_def <dbl>
Paket rvest, salah satu yang paling berguna dari tidyverse, memungkinkan kita mengimpor langsung dari html. Misalnya, untuk mengekspor tabel wikipedia gunakan read_html() untuk mengimpor html, html_element("table") untuk mengekstrak objek tabel, dan html_table() untuk mengonversi ke tibble.
Attaching package: 'rvest'
The following object is masked from 'package:readr':
guess_encoding
# A tibble: 24 × 4
Mark Athlete Place Date
<chr> <chr> <chr> <chr>
1 6.97 m (22 ft 10+1⁄4 in) T. Rodgers (USA) San Fr… 5 Ja…
2 6.98 m (22 ft 10+3⁄4 in) Harry Worthington (USA) Hanove… 8 Ma…
3 7.11 m (23 ft 3+3⁄4 in) Aleksander Klumberg (EST) Tartu 19 D…
4 7.49 m (24 ft 6+3⁄4 in) William DeHart Hubbard (USA) Urbana 1 Ma…
5 7.50 m (24 ft 7+1⁄4 in) William DeHart Hubbard (USA) New Yo… 20 M…
6 7.70 m (25 ft 3 in) Jesse Owens (USA) New Yo… 24 F…
7 7.71 m (25 ft 3+1⁄2 in) Eulace Peacock (USA) New Yo… 23 F…
8 7.82 m (25 ft 7+3⁄4 in) Jesse Owens (USA) New Yo… 23 F…
9 7.85 m (25 ft 9 in) Jesse Owens (USA) New Yo… 23 F…
10 7.86 m (25 ft 9+1⁄4 in) Irvin Roberson (USA) New Yo… 20 F…
# ℹ 14 more rows
Opsi lain (terutama jika bekerja dengan orang lain) adalah mengimpor dari spreadsheet Google Drive, menggunakan read_sheet() dari paket googlesheets4.
Pertama kali kamu akan diminta izin tidyverse untuk berinteraksi dengan drive-mu
Opsi menarik lain adalah mengunduh data dari API: perantara antara aplikasi atau penyedia data dan R kita. Misalnya, mari muat pustaka {owidR}, yang memungkinkan mengunduh data dari https://ourworldindata.org/. Fungsi owid_covid() memuat lebih dari 400.000 catatan dengan lebih dari 60 variabel dari 238 negara.
Dalam banyak kesempatan untuk terhubung ke API kita harus terlebih dahulu mendaftar dan mendapatkan kunci, ini adalah kasus paket climaemet untuk mengakses data meteorologi Spanyol (https://opendata.aemet.es/centrodedescargas/inicio).
Setelah kita memiliki kunci API kita mendaftarkannya di RStudio agar dapat digunakan di masa depan.
library(climaemet)
# Api key
apikey <- "eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOiJqYXZhbHYwOUB1Y20uZXMiLCJqdGkiOiI4YTU1ODUxMS01MTE3LTQ4MTYtYmM4OS1hYmVkNDhiODBkYzkiLCJpc3MiOiJBRU1FVCIsImlhdCI6MTY2NjQ2OTcxNSwidXNlcklkIjoiOGE1NTg1MTEtNTExNy00ODE2LWJjODktYWJlZDQ4YjgwZGM5Iiwicm9sZSI6IiJ9.HEMR77lZy2ASjmOxJa8ppx2J8Za1IViurMX3p1reVBU"
aemet_api_key(apikey, install = TRUE)Dengan paket ini kita dapat melakukan pencarian stasiun untuk mengetahui kode pos dan kode identifikasinya dalam jaringan AEMET
Misalnya, untuk mendapatkan data dari stasiun bandara El Prat, Barcelona, kode yang diberikan adalah "0076", mendapatkan data per jam
Salah satu alat paling berguna dalam beberapa tahun terakhir dikenal sebagai tidycensus: alat untuk memfasilitasi proses mengunduh data sensus untuk Amerika Serikat dari R.
get_decennial(): untuk mengakses data sensus (Sensus Sepuluh Tahunan AS), dilakukan setiap 10 tahun (tahun 2000, 2010, dan 2020).
get_acs(): untuk mengakses ACS (American Community Survey) tahunan dan lima tahunan (sensus ≠ survei)
get_estimates(): untuk mengakses perkiraan populasi, kelahiran, dan kematian tahunan
get_pums(): untuk mengakses mikro data (tidak teragregasi) dari ACS (dianonimkan di tingkat individu)
get_flows(): untuk mengakses data aliran migrasi.
Misalnya, kita akan mengunduh data sensus (get_decennial()) di tingkat negara bagian (geography = "state") untuk populasi (variabel variables = "P001001") tahun 2010 (lihat variabel dalam tidycensus::load_variables()).
Opsi lainnya:
{chessR}: data pertandingan catur. Lihat https://github.com/JaseZiv/chessR
spotifyr: data dari Spotify. Lihat https://www.rcharlie.com/spotifyr/
gtrendsR: data dari Google Trends. Lihat https://github.com/PMassicotte/gtrendsR
scholar: data dari https://github.com/jkeirstead/scholar
Try to solve the following exercises without looking at the solutions
📝 Dataset who yang sudah kita gunakan dalam latihan sebelumnya, ekspor ke format native R dalam folder data proyek.
📝 Muat dataset who dari folder data (impor file yang dibuat dalam latihan sebelumnya).
📝 Ulangi hal yang sama (ekspor dan impor) dalam 4 format: .csv, .xlsx, .sav (spss), dan .dta (stata).
# csv
library(readr)
write_csv(who, file = "./data/who.csv")
who_data <- read_csv(file = "./data/who.csv")
# excel
library(openxlsx)
write.xlsx(who, file = "./data/who.xlsx")
who_data <- read_xlsx(path = "./data/who.xlsx")
# sas y stata
library(haven)
write_sav(who, path = "./data/who.sav")
who_data <- read_spss(path = "./data/who.sav")
write_dta(who, path = "./data/who.dta")
who_data <- read_dta(path = "./data/who.dta")Kita akan mempraktikkan pemuatan dan pra-pemrosesan file dari SPSS. File berisi data dari barometer CIS «Persepsi tentang kesetaraan antara pria dan wanita dan stereotip gender» (ekstensi .sav dalam subfolder CIS-feminism) yang pekerjaan sampelnya dilakukan 6–14 November (4000 wawancara, kedua jenis kelamin, usia >16 tahun, 1174 kotamadya, 50 provinsi).
Coba jawab pertanyaan-pertanyaan yang ada di workbook
Menangani faktor dan list
Kita sudah melihat bahwa list adalah objek di R yang memungkinkan kita menyimpan koleksi variabel bertipe berbeda (seperti dengan data.frame dan tibble) tetapi juga panjang yang berbeda, dengan struktur sepenuhnya heterogen (bahkan sebuah list bisa memiliki list lain di dalamnya).
Kita juga dapat membuat list dengan list lain di dalamnya, sehingga untuk mengakses setiap level kita harus menggunakan operator [[]].
[1] "list_1" "list_2"
We are allowed to store n-dimensional data!
Salah satu kekurangannya adalah list tidak dapat divektorisasi secara langsung, sehingga operasi aritmatika yang diterapkan pada list akan memberikan error.
Error in data/2: non-numeric argument to binary operator
Opsi yang lebih fleksibel dan serbaguna adalah menggunakan paket purrr dari lingkungan tidyverse.
Paket ini dimaksudkan untuk meniru pemrograman fungsional dari bahasa lain seperti Scala atau strategi map-reduce Hadoop (dari Google).
Fungsi paling sederhana dari paket purrr adalah fungsi map(), yang menerapkan fungsi tervektorisasi ke setiap elemen list. Mari lihat contoh pertama yang diterapkan pada vektor
map() allows us to “map” each list and apply the function element by element (if applicable).
Be careful
Dengan vektor kita memiliki vektorisasi default karena R melakukan operasi elemen per elemen. Perhatikan bahwa, secara default, output dari map adalah list.
Mari lihat contoh lain. Definisikan dalam sebuah list dua sampel dari 2 distribusi normal, dengan ukuran sampel dan rata-rata yang berbeda. Hitung rata-rata masing-masing.
Bagaimana jika kita ingin menghitung rata-rata dari nilai kuadratnya?
Selain lebih mudah dibaca dan efisien, dengan purrr kita dapat memutuskan format output setelah operasi
map_dbl()
map_int()
map_chr()
map_lgl()
Juga, jika kamu meneruskan angka alih-alih fungsi, itu akan mengembalikan elemen ke-i dari setiap list.
Kita juga dapat menggunakan pluck() untuk mengakses elemen ke-i dari sebuah list
# A tibble: 87 × 14
name height mass hair_color skin_color eye_color birth_year sex
<chr> <int> <dbl> <chr> <chr> <chr> <dbl> <chr>
1 Luke… 172 77 blond fair blue 19 male
2 C-3PO 167 75 <NA> gold yellow 112 none
3 R2-D2 96 32 <NA> white, bl… red 33 none
4 Dart… 202 136 none white yellow 41.9 male
5 Leia… 150 49 brown light brown 19 fema…
6 Owen… 178 120 brown, gr… light blue 52 male
7 Beru… 165 75 brown light blue 47 fema…
8 R5-D4 97 32 <NA> white, red red NA none
9 Bigg… 183 84 black light brown 24 male
10 Obi-… 182 77 auburn, w… fair blue-gray 57 male
# ℹ 77 more rows
# ℹ 6 more variables: gender <chr>, homeworld <chr>, species <chr>,
# films <list>, vehicles <list>, starships <list>
Kita juga memiliki opsi untuk menggeneralisasikannya agar dapat menggunakan fungsi yang membutuhkan dua argumen dalam bentuk list (operasi biner), dengan map2()
Kita dapat memperoleh output dalam bentuk data.frame dengan menambahkan list_rbind() atau list_cbind(), yang mengonversi list menjadi tabel.
Kita dapat menggeneralisasikannya lebih lanjut dengan pmap_xxx() yang memungkinkan penggunaan beberapa argumen (beberapa list).
Kita memiliki jenis iterator lain yang, meskipun menerima input, tidak mengembalikan apa-apa, seperti walk() (satu argumen), walk2() (dua argumen) dan pwalk() (beberapa argumen), semuanya mengembalikan secara tidak terlihat, hanya memanggil fungsi untuk efek sampingnya.
📝 Definisikan list dengan 4 elemen bertipe berbeda dan akses yang kedua (saya akan menyertakan satu yang berupa tibble agar kamu dapat melihat bahwa dalam list ada ruang untuk segalanya).
📝 Dari list di atas, akses elemen yang menempati posisi 1 dan 4.
📝 Muat dataset starwars dari paket dplyr dan akses film kedua yang muncul dalam starwars$films (untuk setiap karakter). Tentukan mana yang tidak muncul di lebih dari satu film.
[1] FALSE FALSE FALSE FALSE FALSE FALSE FALSE TRUE TRUE FALSE FALSE
[12] FALSE FALSE FALSE TRUE FALSE FALSE TRUE FALSE FALSE FALSE TRUE
[23] TRUE FALSE TRUE FALSE TRUE TRUE TRUE TRUE TRUE FALSE TRUE
[34] FALSE FALSE TRUE TRUE TRUE FALSE TRUE TRUE FALSE TRUE TRUE
[45] FALSE TRUE TRUE TRUE TRUE FALSE FALSE FALSE FALSE FALSE FALSE
[56] TRUE FALSE FALSE TRUE TRUE TRUE FALSE FALSE TRUE TRUE FALSE
[67] FALSE TRUE TRUE TRUE TRUE TRUE TRUE FALSE TRUE TRUE FALSE
[78] TRUE TRUE FALSE FALSE TRUE TRUE TRUE TRUE TRUE TRUE
Dalam statistik, ketika kita membicarakan variabel kualitatif, kita akan menyebut level atau modalitas sebagai nilai-nilai berbeda yang dapat diambil data tersebut. Misalnya, untuk variabel sex dalam set starwars, kita memiliki 4 level yang diizinkan: female, hermaphroditic, male dan none (di samping data hilang).
Jenis variabel ini dikenal dalam R sebagai faktor, dan paket fundamental untuk menanganinya adalah forcats (dari lingkungan tidyverse).
Paket ini memungkinkan kita menetapkan level (disimpan secara internal sebagai levels) yang diambil variabel kategoris sehingga tidak ada kesalahan dalam pengumpulan dan pembuatan data. Ini juga membuat analisisnya lebih hemat komputasi, memberikan perlakuan yang berbeda dari string teks biasa.
Mari lihat contoh sederhana mensimulasikan variabel party dengan nilai "PP", "PSOE", dan "SUMAR" (ukuran 15)
[1] "PP" "PSOE" "SUMAR" "PP" "PP" "SUMAR" "PSOE" "SUMAR"
[9] "SUMAR" "SUMAR" "PP" "PSOE" "PP" "PSOE" "SUMAR"
Variabel party saat ini bertipe teks, tipe chr, yang dapat diperiksa dengan class(state).
Dari sudut pandang statistik dan komputasi, untuk R variabel ini sekarang setara dengan variabel bernama. Tetapi secara statistik variabel sebagai string tidak sama dengan variabel kategoris yang hanya dapat mengambil 3 level tersebut. Bagaimana cara mengonversi ke faktor?
Dengan menggunakan fungsi as_factor() dari paket forcats.
Tidak hanya kelas variabel yang berubah, tetapi sekarang, di bawah nilai yang disimpan, kalimat Levels: ... muncul: itulah modalitas atau level dari variabel kualitatif kita.
Bayangkan kita mendefinisikan database anggota parlemen dan anggota PP tidak hadir hari itu: meskipun variabel kita tidak mengambil nilai itu HARI ITU, nilai PSOE adalah level yang diizinkan dalam database (sehingga bahkan jika kita menghapusnya, karena itu faktor, level tetap ada).
Dengan fungsi factor() kita dapat secara eksplisit menentukan nama-nama modalitas dan menggunakan levels = ... kita dapat secara eksplisit memberi tahu “urutan” modalitas
“Urutan” sebelumnya hanya dalam arti mana yang akan dihitung/digambar pertama) tetapi kita belum memiliki variabel ordinal
Warning in Ops.factor(party_fct$party, "SUMAR"): '<' not meaningful
for factors
[1] NA NA NA NA NA NA NA NA NA NA NA NA NA NA NA
Bagaimana jika kita ingin mendefinisikan variabel kualitatif ORDINAL? Di dalam factor() kita harus menunjukkan bahwa ordered = TRUE.
[1] A E F B A+ A C C D B A C C E F D A+
Levels: F < E < D < C < B < A < A+
Apa yang berubah? Jika kamu perhatikan sekarang, meskipun variabel masih kualitatif, kita dapat membuat perbandingan dan mengurutkan catatan karena ada hierarki antara modalitas.
Jika kita ingin menghapus level yang tidak digunakan saat itu (yang ingin kita kecualikan dari definisi) kita dapat melakukannya dengan fct_drop().

Sama seperti kita dapat menghapus level, kita dapat memperluas level yang ada (bahkan jika tidak ada data untuk level itu saat ini) dengan fct_expand().

Selain itu dengan fct_explicit_na() kita dapat menetapkan level untuk nilai yang hilang agar disertakan dalam analisis dan visualisasi.

Bahkan setelah didefinisikan kita dapat mengurutkan ulang level dengan fct_relevel().
Cara bekerja dengan variabel kualitatif ini memungkinkan kita memberikan definisi teoritis dari database kita, dan kita bahkan dapat menghitung nilai yang belum ada (tetapi bisa ada), menggunakan fct_count().

Level juga dapat diurutkan berdasarkan frekuensi dengan fct_infreq().
[1] A E F B A+ A C C D B A C C E F D A+
Levels: C < A < F < E < D < B < A+
# A tibble: 7 × 2
f n
<ord> <int>
1 C 4
2 A 3
3 F 2
4 E 2
5 D 2
6 B 2
7 A+ 2
Terkadang kita ingin mengelompokkan level, misalnya, tidak mengizinkan level yang tidak muncul minimal sejumlah kali dengan fct_lump_min(..., min = ..) (pengamatan yang tidak memenuhi ini akan masuk ke level generik bernama Other).
Kita dapat melakukan sesuatu yang setara tetapi berdasarkan frekuensi relatif dengan fct_lump_prop().
Kita dapat menerapkan ini pada dataset kita untuk mengkategorikan ulang variabel dengan sangat cepat.
Dengan fct_reorder() kita juga dapat menunjukkan bahwa kita ingin mengurutkan faktor sesuai dengan fungsi yang diterapkan pada variabel lain.
[1] Human Droid Droid Human Human Human Human Droid Human
[10] Human Human Human Others Human Others Others Human Others
[19] Human Human Droid Others Human Human Others Human Others
[28] Others Human Others Human Human Gungan Gungan Gungan Human
[37] Others Others Human Human Others Others Others Others Others
[46] Others Others Human Others Others Others Others Others Others
[55] Others Others Human Others Others Others Human Human Human
[64] Human Others Others Others Others Human Droid Others Others
[73] Others Others Others Human Others
Levels: Droid Gungan Human Others
[1] Human Droid Droid Human Human Human Human Droid Human
[10] Human Human Human Others Human Others Others Human Others
[19] Human Human Droid Others Human Human Others Human Others
[28] Others Human Others Human Human Gungan Gungan Gungan Human
[37] Others Others Human Human Others Others Others Others Others
[46] Others Others Human Others Others Others Others Others Others
[55] Others Others Human Others Others Others Human Human Human
[64] Human Others Others Others Others Human Droid Others Others
[73] Others Others Others Human Others
Levels: Droid Others Human Gungan
📝 Diberikan variabel months di bawah ini (vektor karakter), konversikan ke faktor.
📝 Diberikan variabel months di bawah ini, konversikan ke faktor dengan menunjukkan level yang benar.
📝 Hitung berapa banyak nilai untuk setiap bulan, ingat ini faktor (mungkin ada level yang tidak digunakan, hasilnya 0).
📝 Karena ada nilai hilang, tetapkan level ketiga belas berlabel "missing".
Kita akan bekerja lagi dengan file berisi data dari barometer CIS (Centro de Investigaciones Sociológicas) «Perceptions on equality between men and women and gender stereotypes» whose sample work was carried out from November 6 to 14 (4000 interviews of both sexes over 16 years old in 1174 municipalities and 50 provinces).
Coba jawab pertanyaan-pertanyaan yang ada di workbook
Kita akan memperkenalkan paket dbplyr, yang memungkinkan kita menggabungkan kode SQL ke dalam R untuk melakukan kueri database
Jika kamu menggunakan R untuk analisis data, sebagian besar data yang dibutuhkan mungkin sudah ada dalam database. Kita akan belajar cara memuat data ke database lokal.
Kita juga perlu menginstal paket backend DBI (antarmuka yang memungkinkan dplyr bekerja dengan banyak database berbeda menggunakan kode yang sama). Lima backend yang umum digunakan adalah:
RMariaDB connects to MySQL and MariaDB
RPostgres connects to Postgres and Redshift.
RSQLite embeds a SQLite database.
odbc connects to many commercial databases via the open database connectivity protocol.
bigrquery connects to Google’s BigQuery.
Selanjutnya, kita akan menggunakan backend RSQLite (secara otomatis terinstal saat menginstal dbplyr).
Jika kita ingin bekerja dengan database menggunakan tata bahasa dplyr, kita harus terlebih dahulu terhubung ke sana. Koneksi dilakukan dengan DBI::dbConnect(). Argumen DBI::dbConnect() bervariasi dari database ke database, tetapi argumen pertama selalu backend database. SQLite hanya membutuhkan path ke database.
<SQLiteConnection>
Path: :memory:
Extensions: TRUE
Here, the string ":memory:" is a special path that creates a temporary in-memory database.
Database sementara yang dibuat sebelumnya belum memiliki data. Kita akan menyalin database yang ada (misalnya, gapminder dari paket gapminder) menggunakan copy_to(). Menggunakan tbl() kita “mendapatkan” database (disebut sesuai nama dalam copy_to()).
Perbedaan utamanya adalah sekarang ini adalah sumber jarak jauh dalam database SQLite.
# Source: table<`gapminder_database`> [?? x 6]
# Database: sqlite 3.50.4 [:memory:]
country continent year lifeExp pop gdpPercap
<chr> <chr> <int> <dbl> <int> <dbl>
1 Afghanistan Asia 1952 28.8 8425333 779.
2 Afghanistan Asia 1957 30.3 9240934 821.
3 Afghanistan Asia 1962 32.0 10267083 853.
4 Afghanistan Asia 1967 34.0 11537966 836.
5 Afghanistan Asia 1972 36.1 13079460 740.
6 Afghanistan Asia 1977 38.4 14880372 786.
7 Afghanistan Asia 1982 39.9 12881816 978.
8 Afghanistan Asia 1987 40.8 13867957 852.
9 Afghanistan Asia 1992 41.7 16317921 649.
10 Afghanistan Asia 1997 41.8 22227415 635.
# ℹ more rows
Tujuan utama dbplyr adalah secara otomatis menghasilkan SQL dari tata bahasa dplyr yang sudah kita kenal.
# Source: SQL [?? x 3]
# Database: sqlite 3.50.4 [:memory:]
country year lifeExp
<chr> <int> <dbl>
1 Afghanistan 1952 28.8
2 Afghanistan 1957 30.3
3 Afghanistan 1962 32.0
4 Afghanistan 1967 34.0
5 Afghanistan 1972 36.1
6 Afghanistan 1977 38.4
7 Afghanistan 1982 39.9
8 Afghanistan 1987 40.8
9 Afghanistan 1992 41.7
10 Afghanistan 1997 41.8
# ℹ more rows
Perbedaan terpenting adalah sekarang kode R kita diterjemahkan ke SQL dan dieksekusi di database di server jarak jauh, bukan di R di mesin lokalmu: tidak pernah menarik data ke R kecuali kamu secara eksplisit memintanya, menunda pekerjaan hingga momen terakhir yang memungkinkan.
Baru saat kita meminta data (menulis gapminder_query di konsol, misalnya), verb dplyr menghasilkan SQL dan meminta hasilnya dari database.
# Source: SQL [?? x 3]
# Database: sqlite 3.50.4 [:memory:]
country year lifeExp
<chr> <int> <dbl>
1 Afghanistan 1952 28.8
2 Afghanistan 1957 30.3
3 Afghanistan 1962 32.0
4 Afghanistan 1967 34.0
5 Afghanistan 1972 36.1
6 Afghanistan 1977 38.4
7 Afghanistan 1982 39.9
8 Afghanistan 1987 40.8
9 Afghanistan 1992 41.7
10 Afghanistan 1997 41.8
# ℹ more rows
Apa yang terjadi di balik layar?
dplyr menerjemahkan kode R kita ke verb SQL, yang dapat kita periksa (tanpa melakukan) dengan menggunakan show_query()
Seperti yang dikomentari, kueri database jarak jauh kita tidak ada di R di mesin lokalmu: tidak pernah menarik data ke R kecuali kamu secara eksplisit memintanya. Kamu dapat mengulangi beberapa kali sebelum mengetahui data yang dibutuhkan, lalu gunakan collect().
# A tibble: 1,704 × 3
country year lifeExp
<chr> <int> <dbl>
1 Afghanistan 1952 28.8
2 Afghanistan 1957 30.3
3 Afghanistan 1962 32.0
4 Afghanistan 1967 34.0
5 Afghanistan 1972 36.1
6 Afghanistan 1977 38.4
7 Afghanistan 1982 39.9
8 Afghanistan 1987 40.8
9 Afghanistan 1992 41.7
10 Afghanistan 1997 41.8
# ℹ 1,694 more rows
Kamu juga dapat menggunakan translate_sql() untuk menerjemahkan ekspresi individual dari dplyr ke SQL