Ini mungkin sesuatu yang umum dan sepele, tetapi saya tampaknya kesulitan menemukan jawaban yang konkret. Dalam C # ada konsep delegasi, yang sangat terkait dengan gagasan fungsi pointer dari C ++. Apakah ada fungsi serupa di Jawa? Mengingat bahwa pointer agak tidak ada, apa cara terbaik tentang ini? Dan untuk lebih jelasnya, kita berbicara kelas satu di sini.
java
pointers
delegates
function-pointers
rambut gimbal
sumber
sumber
this::myMethod
secara semantik sama dengan menciptakan lambdaparamA, paramB -> this.myMethod(paramA, paramB)
.Jawaban:
Idiom Java untuk fungsionalitas fungsi-pointer-suka adalah kelas anonim yang mengimplementasikan antarmuka, misalnya
Pembaruan: hal-hal di atas diperlukan dalam versi Java sebelum Java 8. Sekarang kami memiliki alternatif yang lebih baik, yaitu lambdas:
dan referensi metode:
sumber
std::bind
, yang mengikat parameter ke fungsi dan mengembalikan objek yang bisa dipanggil. Saya tidak bisa membela C atas dasar ini, tetapi C ++ benar - benar lebih baik daripada Java untuk ini.Anda bisa mengganti penunjuk fungsi dengan antarmuka. Katakanlah Anda ingin menjalankan koleksi dan melakukan sesuatu dengan setiap elemen.
Ini adalah antarmuka yang bisa kita berikan kepada beberapa orang mengatakan CollectionUtils2.doFunc (Collection c, IFunction f).
Sebagai contoh katakanlah kami memiliki koleksi angka dan Anda ingin menambahkan 1 ke setiap elemen.
sumber
Anda dapat menggunakan refleksi untuk melakukannya.
Lulus sebagai parameter objek dan nama metode (sebagai string) dan kemudian memanggil metode. Sebagai contoh:
Dan kemudian gunakan seperti pada:
Tentu saja, periksa semua pengecualian dan tambahkan gips yang dibutuhkan.
sumber
Tidak, fungsi bukan objek kelas satu di java. Anda dapat melakukan hal yang sama dengan menerapkan kelas penangan - ini adalah bagaimana panggilan balik diterapkan dalam Swing dll.
Namun ada proposal untuk penutupan (nama resmi untuk apa yang Anda bicarakan) di versi masa depan java - Javaworld memiliki artikel yang menarik.
sumber
Ini mengingatkan saya pada Eksekusi Steve Yegge di Kerajaan Kata Benda . Pada dasarnya menyatakan bahwa Java membutuhkan objek untuk setiap tindakan, dan karena itu tidak memiliki entitas "hanya-kata kerja" seperti pointer fungsi.
sumber
Untuk mencapai fungsionalitas serupa, Anda bisa menggunakan kelas dalam anonim.
Jika Anda mendefinisikan antarmuka
Foo
:Buat metode
bar
yang akan menerima 'penunjuk fungsi' sebagai argumen:Akhirnya panggil metode tersebut sebagai berikut:
sumber
Java8 telah memperkenalkan lambdas dan referensi metode . Jadi, jika fungsi Anda cocok dengan antarmuka fungsional (Anda dapat membuatnya sendiri), Anda dapat menggunakan referensi metode dalam kasus ini.
Java menyediakan satu set antarmuka fungsional umum . sedangkan Anda bisa melakukan hal berikut:
sumber
alias
: egpublic List<T> collect(T t) = Collections::collect
Tidak ada yang seperti itu di Jawa. Anda perlu membungkus fungsi Anda menjadi beberapa objek dan meneruskan referensi ke objek itu untuk meneruskan referensi ke metode pada objek itu.
Secara sintaksis, ini dapat dikurangi sampai batas tertentu dengan menggunakan kelas anonim yang didefinisikan di tempat atau kelas anonim yang didefinisikan sebagai variabel anggota kelas.
Contoh:
sumber
Saya telah menerapkan dukungan panggilan balik / delegasi di Jawa menggunakan refleksi. Detail dan sumber kerja tersedia di situs web saya .
Bagaimana itu bekerja
Kami memiliki kelas prinsip bernama Callback dengan kelas bersarang bernama WithParms. API yang membutuhkan panggilan balik akan mengambil objek Callback sebagai parameter dan, jika perlu, buat Callback. Karena banyak sekali aplikasi objek ini akan bersifat rekursif, ini bekerja dengan sangat bersih.
Dengan kinerja yang masih merupakan prioritas tinggi bagi saya, saya tidak ingin diharuskan untuk membuat array objek sekali pakai untuk menyimpan parameter untuk setiap doa - setelah semua dalam struktur data besar mungkin ada ribuan elemen, dan dalam pemrosesan pesan skenario kita akhirnya bisa memproses ribuan struktur data per detik.
Untuk menjadi threadsafe, array parameter harus ada secara unik untuk setiap pemanggilan metode API, dan untuk efisiensi yang sama harus digunakan untuk setiap pemanggilan callback; Saya membutuhkan objek kedua yang akan lebih murah untuk dibuat untuk mengikat panggilan balik dengan array parameter untuk doa. Tetapi, dalam beberapa skenario, penyerang akan sudah memiliki array parameter karena alasan lain. Karena dua alasan ini, array parameter tidak termasuk dalam objek Callback. Juga pilihan doa (melewati parameter sebagai array atau sebagai objek individual) berada di tangan API menggunakan panggilan balik yang memungkinkannya untuk menggunakan doa mana saja yang paling cocok untuk pekerjaan dalam dirinya.
Kelas bersarang WithParms, kemudian, adalah opsional dan melayani dua tujuan, ini berisi array objek parameter yang diperlukan untuk panggilan balik, dan menyediakan 10 metode pemanggilan () yang berlebihan (dengan dari 1 hingga 10 parameter) yang memuat array parameter dan kemudian aktifkan target panggilan balik.
sumber
Periksa penutupan bagaimana mereka telah diterapkan di perpustakaan lambdaj. Mereka sebenarnya memiliki perilaku yang sangat mirip dengan delegasi C #:
http://code.google.com/p/lambdaj/wiki/Closures
sumber
Relatif untuk kebanyakan orang di sini saya baru mengenal java tetapi karena saya belum melihat saran serupa saya punya alternatif lain untuk menyarankan. Saya tidak yakin apakah ini praktik yang baik atau tidak, atau bahkan menyarankan sebelumnya dan saya tidak mengerti. Saya suka karena saya pikir itu deskriptif sendiri.
kemudian tergantung pada aplikasinya, tetapkan
dll.
dan menelepon
sumber