Kueri paralel di Kotlin untuk mengotomatiskan pengumpulan data

Halo semuanya! Dalam pekerjaan saya, saya sering menggunakan Kotlin untuk otomatisasi. Aktivitas saya tidak terkait langsung dengan pemrograman, tetapi Kotlin sangat menyederhanakan tugas kerja.





Baru-baru ini perlu mengumpulkan data dengan ukuran yang agak besar untuk melakukan analisis, jadi saya memutuskan untuk menulis skrip kecil untuk mendapatkan data dan menyimpannya di Excel. Tidak ada masalah dengan poin terakhir - saya membaca tentang Apache POI, mengambil beberapa contoh dari dokumentasi resmi, memodifikasinya sendiri. Hal yang sama tidak dapat dikatakan tentang permintaan Internet.





Sumber kembali dalam batch json dan diperlukan untuk mengumpulkan "batch" ini dengan cepat, mengubahnya menjadi teks dan menulis tabel ke file.





Metode asynchronous

Saya memutuskan untuk memulai dengan asinkronisasi sederhana. Setelah melihat-lihat HttpUrlConnection sedikit, saya mengirimkannya ke tempatnya, menggantinya dengan HttpClient dari Java.





Untuk pengujian, saya menggunakan layanan https://jsonplaceholder.typicode.com/ , yang disarankan oleh satu pengembang yang saya kenal. Saya menyimpan tautan yang mengeluarkan Json dengan komentar ke variabel, agar tidak menduplikasi dan memulai tes.





const val URL = "https://jsonplaceholder.typicode.com/comments"
      
      



Fungsinya sudah siap dan bahkan berfungsi. Datanya masuk.





fun getDataAsync(url: String): String? {
    val httpClient = HttpClient.newBuilder()
        .build()
    val httpRequest = HttpRequest.newBuilder()
        .uri(URI.create(link)).build()

    return httpClient.sendAsync(httpRequest, BodyHandlers.ofString())
        .join().body()
}
      
      



Sekarang perlu untuk memeriksa kecepatan kerja. Dipersenjatai dengan measureTimeMillis, saya menjalankan kodenya.





val asyncTime = measureTimeMillis { 
    val res = (1..10)
        .toList()
        .map {getDataAsync("$URL/$it")}
    res.forEach { println(it) }
}
println("   $asyncTime ")
      
      



Semuanya bekerja sebagaimana mestinya, tetapi saya menginginkannya lebih cepat. Setelah sedikit menggali di Internet, saya menemukan solusi di mana tugas dilakukan secara paralel.





Peta Paralel

, . , , .





suspend fun <A, B> Iterable<A>.pmap(f: suspend (A) -> B): List<B> =
    coroutineScope {
        map { async { f(it) } }.awaitAll()
    }
      
      



, ( Iterable) pmap, . A. async , .awaitAll() . suspend, .





, , - .





val parmapTime = measureTimeMillis {
    runBlocking {
        val res = (1..10)
            .toList()
            .pmap { getDataAsync("$URL/$it") }
        println(mapResult)
    }
}
println(" pmap $parmapTime ")
      
      



- 1523, . map async, .





Parallel Map v 2.0

, , .





suspend fun <T, V> Iterable<T>.parMap(func: suspend (T) -> V): Iterable<V> =
    coroutineScope {
        map { element -> 
            async(Dispatchers.IO) { func(element) } 
        }.awaitAll() 
    }

val parMapTime = measureTimeMillis {
    runBlocking {
        val res = (1..10)
            .toList()
            .parMap { getDataAsync("$URL/$it") }
    }
    println(res)
}
println(" map  $parMapTime ")
      
      



Dispatchers.IO 2 ~ 610 . ! ( , excel ..) . , - .





Java ParallelStream

, stackowerflow parallelStream. , IDEA.





val javaParallelTime = measureTimeMillis { 
    val res = (1..10).toList()
        .parallelStream()
        .map { getDataAsync("$URL/$it") }
    res.forEach { println(it) }
}
println("Java parallelSrtream  $javaParallelTime ")
      
      



, . , . stream . , , , "" , Json.





, - , async . .





Hasilnya dapat dilihat pada tabel di bawah ini. Untuk diri saya sendiri, saya pasti memutuskan untuk meninggalkan async menunggu . Terutama karena penanganan error yang lebih sederhana, tentunya. Dan tidak perlu melampaui coroutine di sini.





metode





Waktu (md)





Metode asynchronous





1487





Implementasi Pmap dari web





1523





Pilihan saya adalah parallelMap





610





Java.parallelStream





578





Di masa depan, ada pemikiran untuk menyusun ini di perpustakaan kecil dan menggunakannya untuk keperluan pribadi, dan tentu saja menulis ulang semuanya dari "kode Hindu" ke kode manusia, asalkan ada cukup kemungkinan. Dan kemudian unggah semuanya ke vds.





Saya berharap pengalaman saya bermanfaat bagi seseorang. Saya akan senang menerima kritik dan nasihat yang membangun! Terimakasih untuk semua








All Articles