Saya menggunakan GNU R di PC Ubuntu-Lucid yang memiliki 4 CPU. Untuk menggunakan semua 4 CPU, saya menginstal paket "r-cran-multicore". Karena manual paket tidak memiliki contoh praktis yang saya mengerti, saya perlu saran tentang cara mengoptimalkan skrip saya untuk menggunakan semua 4 CPU.
Dataset saya adalah data.frame (disebut P1) yang memiliki 50.000 baris dan 1600 cols. Untuk setiap baris, saya ingin menghitung maximun, jumlah dan mean. Script saya terlihat sebagai berikut:
p1max <- 0
p1mean <- 0
p1sum <-0
plength <- length(P1[,1])
for(i in 1:plength){
p1max <- c(p1max, max(P1[i,]))
p1mean <- c(p1mean, mean(P1[i,]))
p1sum <- c(p1sum, sum(P1[i,]))
}
Adakah yang bisa tolong beri tahu saya cara memodifikasi dan menjalankan skrip untuk menggunakan semua 4 CPU?
Jawaban:
Menggunakan foreach dan doMC . Penjelasan terperinci dapat ditemukan di sini . Script Anda akan berubah sangat sedikit, garis
harus diubah menjadi
Prasyarat untuk skrip multitasking yang menggunakan paket ini adalah
Catatan kehati-hatian. Menurut dokumentasi Anda tidak dapat menggunakan ini di GUI.
Sedangkan untuk masalah Anda, apakah Anda benar-benar membutuhkan multitasking? Data.frame Anda membutuhkan sekitar 1,2GB RAM, jadi itu harus sesuai dengan memori Anda. Jadi Anda cukup menggunakan apply:
Hasilnya akan menjadi matriks dengan ringkasan setiap baris.
Anda juga dapat menggunakan fungsi mclapply yang ada dalam paket multicore. Maka skrip Anda mungkin terlihat seperti ini:
Ini akan mengembalikan daftar, di mana elemen ke-i akan menjadi ringkasan dari baris ke-i. Anda dapat mengubahnya menjadi matriks menggunakan sapply
sumber
Anda sudah mendapat jawaban tentang cara menggunakan lebih dari satu inti, tetapi masalah sebenarnya adalah dengan cara Anda menulis loop Anda. Jangan pernah memperluas vektor / objek hasil Anda di setiap iterasi dari satu loop . Jika Anda melakukan ini, Anda memaksa R untuk menyalin vektor hasil / objek Anda dan memperpanjangnya yang semuanya membutuhkan waktu. Alih-alih, pralokasi ruang penyimpanan yang cukup sebelum Anda memulai loop dan isi saat Anda melanjutkan. Berikut ini sebuah contoh:
Atau Anda dapat melakukan hal-hal ini melalui
apply()
:Tetapi perhatikan bahwa ini tidak lebih cepat daripada melakukan loop dengan benar dan kadang-kadang lebih lambat.
Namun, selalu waspada terhadap kode vektor. Anda dapat melakukan jumlah baris dan cara menggunakan
rowSums()
danrowMeans()
mana yang lebih cepat daripada loop atauapply
versi:Jika saya seorang pemain taruhan, saya akan mendapatkan uang untuk pendekatan ketiga yang saya sebut pemukulan
foreach()
atau opsi multi-core lainnya dalam tes kecepatan pada matriks Anda karena mereka harus mempercepat banyak hal untuk membenarkan biaya overhead yang dikeluarkan dalam mengatur proses terpisah yang bertani core CPU yang berbeda.Pembaruan: Mengikuti komentar dari @shabbychef apakah lebih cepat untuk melakukan penjumlahan sekali dan menggunakan kembali dalam perhitungan mean?
Tidak dalam uji coba ini, tetapi ini masih jauh dari lengkap ...
sumber
rowSums
untuk menghitung rata-rata baris (kecuali jika saya melewatkan sesuatu mengenai misalnya Na atau NaN). Kode dalam pendekatan ketiga Anda menjumlahkan setiap kolom dua kali .rowSums
danrowMeans
kode kompilasi yang sangat dioptimalkan dan apa yang kita peroleh hanya dengan menghitung penjumlahan sekali, kita kehilangan lagi dalam melakukan perhitungan rata-rata dalam kode yang ditafsirkan.system.time({ for (iii in c(1:1000)) { p1max3 <- apply(p1, 1, max) p1mean3 <- rowMeans(p1) p1sum3 <- rowSums(p1) } })
dan serupasystem.time({ for (iii in c(1:1000)) { p1max4 <- apply(p1, 1, max) p1sum4 <- rowSums(p1) p1mean4 <- p1sum4 / ncol(p1) } })
; versi yang tidak menghitung ulang jumlah membutuhkan 1,368 detik di komputer saya; yang membutuhkan waktu 1,396. lagi, jauh dari lengkap, tetapi lebih menarik ...rowMeans
dan ketikarowSums
diimplementasikan dalam kode kompilasi yang efisien dan dioptimalkan, mereka akan sulit dikalahkan.rowMean
akan sulit dikalahkan melalui alat R tujuan umum seperti*apply
. Namun, Anda tampaknya menyarankan bahwa lebih cepat untuk menjumlahkan 10.000 angka dua kali melaluirowMean
danrowSum
daripada hanya sekali dan menggunakan operator divisi builtin R. Saya tahu R memiliki beberapa masalah efisiensi ( misalnya penemuan kurung kurawal vs masalah kurung), tapi itu sepertinya gila.Silahkan lihat di salju dan hujan salju paket. Banyak contoh dengan ...
Jika Anda ingin mempercepat kode spesifik itu daripada belajar tentang R dan paralelisme, Anda harus melakukannya
sumber