Novice to node.js, apa keuntungan yang diperoleh dengan menggunakan panggilan balik atas peristiwa?

24

Saya pemula JavaScripter dan tidak memiliki pengetahuan nyata tentang apa yang terjadi di dalam mesin V8.

Karena itu, saya benar-benar menikmati perampokan awal saya ke lingkungan node.js tapi saya menemukan bahwa saya terus-menerus menggunakan peristiwa .EventEmitter () sebagai sarana untuk memancarkan acara global sehingga saya dapat menyusun program saya agar sesuai dengan pengamat-pengamat Pola yang mirip dengan apa yang akan saya tulis mengatakan program Objective-C atau Python.

Saya selalu melakukan hal-hal seperti ini:

var events = require('events');

var eventCenter = new events.EventEmitter();

eventCenter.on('init', function() {
    var greeting = 'Hello World!';
    console.log('We're in the init function!);
    eventCenter.emit('secondFunction', greeting);
});

eventCenter.on('secondFunction', function(greeting) {
        console.log('We're in the second function!);
        console.log(greeting);
    eventCenter.emit('nextFunction');
});

eventCenter.on('nextFunction', function {
    /* do stuff */
});

eventCenter.emit('init');

Jadi pada dasarnya saya hanya menyusun kode 'async' node.js menjadi kode yang melakukan hal-hal dalam urutan yang saya harapkan, sebaliknya saya agak "coding mundur" jika itu masuk akal. Apakah akan ada perbedaan dalam melakukan ini dengan cara callback yang berat, baik dari segi kinerja atau dari segi filosofi? Apakah lebih baik melakukan hal yang sama menggunakan panggilan balik alih-alih acara?

Jog
sumber
Jika Anda merasa kode mudah dibaca karena penggunaan callback yang banyak, pertimbangkan untuk menggunakan framework untuk membungkus penggunaan callback Anda. Dibutuhkan sedikit penyesuaian, tetapi janji-janji sering kali dapat mengurai panggilan balik yang jelek. Jika Anda menggunakan JQuery, Anda bisa menggunakan Deferred . Salah satu kerangka janji yang paling sederhana adalah RSVP .
Brian
Saya bingung, saya tidak melihat sesuatu yang asinkron dalam kode Anda, hanya panggilan fungsi yang ditulis dengan cara yang terlalu rumit.
svick

Jawaban:

27

Yang menyenangkan tentang callback adalah tidak ada keadaan global di sana, dan memberikan parameter kepada mereka sepele. Jika Anda memiliki fungsi download(URL, callback: (FileData)->void)maka Anda bisa tahu itu adalah fungsi tingkat tinggi mandiri yang pada dasarnya memungkinkan Anda membangun fungsi "ambil ini dan lakukan itu". Anda dapat memastikan alur kode Anda persis seperti yang Anda harapkan, karena tidak ada orang lain yang memiliki pegangan pada panggilan balik itu, dan panggilan balik itu tidak tahu apa-apa selain parameter fungsi orangtua yang diberikan. Itu membuatnya modular dan mudah untuk diuji.

Jika sekarang Anda ingin mengunduh 5 file secara paralel dan melakukan hal-hal yang berbeda, Anda hanya perlu mematikan lima fungsi ini dengan fungsi panggilan balik yang sesuai. Dalam bahasa dengan sintaks fungsi anonim yang baik ini bisa sangat kuat.

Acara, di sisi lain, lebih dirancang untuk memberi tahu 1..*pengguna tentang beberapa perubahan status. Jika Anda menjalankan acara "unduh lengkap" di akhir download(URL), yang meluncurkan processDownload()yang mengetahui di mana menemukan data, Anda mengikat implementasi hal-hal Anda ke jumlah negara yang lebih besar. Bagaimana Anda memparalelkan unduhan sekarang? Bagaimana Anda menangani unduhan yang berbeda secara berbeda? Apakah download(URL, eventId)elegan? Apakah downloadAndDoThing(URL)elegan? Hampir tidak.

Tentu saja, seperti semua hal lainnya, Anda mendapat untung. Callback bersarang dapat membuat urutan eksekusi kode lebih membingungkan, dan kurangnya accessability global yang mudah membuat pilihan yang buruk untuk apa pun di mana Anda lakukan memiliki 1..*hubungan antara produsen dan konsumen. Anda memiliki waktu yang lebih sulit untuk menyampaikan data, tetapi jika Anda bisa lolos dengan tidak memiliki status tambahan maka itu biasanya menguntungkan.

Bagaimanapun juga. Anda sedang mengkode di node.js di mana panggilan balik bersifat idiomatis, dan bahasa serta pustaka dirancang sesuai penggunaannya. Apakah Anda melihat keuntungan dalam satu desain atau lainnya, saya pikir hampir selalu benar bahwa menulis kode idiomatik dalam bahasa apa pun akan memiliki dukungan yang jauh lebih besar dan membuat hidup Anda jauh lebih mudah daripada mencoba mengelaknya.

Phoshi
sumber
2

Saya tidak pernah menggunakan acara di NodeJS, tetapi secara umum apa yang saya gunakan untuk acara JS di sisi klien adalah menandakan bahwa sesuatu telah terjadi, misalnya, Agenda Pengangkatan, sehingga berbagai bagian tampilan SPA dapat bereaksi terhadap hal itu (tunjukkan dalam timeline, muatkan di panel, dll).
Tetapi menggunakan peristiwa untuk memberi sinyal suatu metode telah selesai dapat menjadi jalan berbahaya untuk bepergian. Anda tidak dapat mengandalkan acara untuk tiba dalam urutan yang sama dengan yang dipecat, sehingga dapat menyebabkan semua jenis keacakan ...
Tidak ada yang salah dengan menggunakan acara, tetapi ada tingkat granularitas tertentu yang tidak boleh Anda ikuti ; jika Anda tetap pada acara domain-ish, itu bagus. Tetapi memberitahukan bahwa metode telah selesai terlalu terperinci.

Stefan Billiet
sumber
0

Sesuatu yang mungkin Anda jelajahi adalah penggunaan peristiwa di luar objek yang memancarkannya. Dalam contoh Anda, eventCentermuncul untuk memancarkan dan menangani acara sendiri. Pertimbangkan bagaimana struktur aplikasi Anda dapat berubah jika objek lain mulai menangani acara.

Jadi, eventCentermungkin memancarkan "init", yang objek lain dapat menangani untuk melakukan kode startup mereka, dll.

Dan1701
sumber