Anda tidak harus meletakkan variabel apa pun di dalam Antarmuka.
cherouvim
34
Karena antarmuka mendefinisikan kontrak yang dapat diimplementasikan dengan berbagai cara. Nilai suatu variabel adalah implementasi.
cherouvim
10
Kita tentu bisa ketika kita tahu semua kelas yang mengimplementasikan antarmuka memiliki beberapa variabel konstan (Misalnya nama bidang).
Aniket Thakur
Apakah ide yang baik untuk membuat variabel di kelas sebagai instance dari antarmuka yang mengimplementasikan kelas? Saya pernah mendengar ini sebelumnya.
Doug Hauf
Antarmuka di java mengikuti prinsip ACID, final karena normalisasi dalam C. @cherouvim Jenis variabel adalah implementasi, variabel harus dideklarasikan, dengan atau tanpa nilai dan definisi variabel adalah nilai. Jika Anda mengubah nilai variabel tidak reimplementation, redefinisi.
Grim
Jawaban:
264
Dari FAQ desain antarmuka Java oleh Philip Shaw:
Variabel antarmuka bersifat statis karena antarmuka Java tidak dapat dipakai pada dirinya sendiri; nilai variabel harus ditetapkan dalam konteks statis di mana tidak ada instance. Pengubah akhir memastikan nilai yang ditetapkan untuk variabel antarmuka adalah konstanta yang benar yang tidak dapat ditugaskan kembali oleh kode program.
Perhatikan bahwa kelas abstrak tidak dapat dipakai "dalam hak mereka sendiri" baik dan mereka dapat memiliki variabel instan.
macias
18
Penjelasan untuk staticpengubah ini sepenuhnya palsu. Variabel instance publik kelas adalah bagian dari antarmuka dan tidak ada alasan mengapa mereka tidak boleh diabstraksi dalam Java interface, sama seperti metode instance. Tidak masalah bahwa Java interfacetidak dapat di-instantiated secara langsung - Anda masih dapat memiliki instance kelas yang mengimplementasikannya interfacedan masuk akal untuk mengharuskan mereka memiliki variabel instance publik tertentu. Adapun bagian tentang final, itu tidak menawarkan penjelasan sama sekali - itu hanya menjelaskan apa finalartinya.
pyrocrasty
3
Kutipan di atas lebih baik dalam konteks. Alasannya adalah "variabel antarmuka dimaksudkan untuk menjadi konstanta Java". Kutipan itu hanya menguraikan mengapa konstanta seperti itu statis dan final. Itu benar, tetapi pertanyaan sebenarnya adalah: mengapa variabel tidak diperbolehkan sebagai bagian dari antarmuka aktual (mis. Menentukan nama dan jenis anggota non-pribadi yang harus terjadi dalam kelas pelaksana). Jika mereka menginginkan "konstanta antarmuka" khusus, mereka dapat menggunakan sintaks baru, atau hanya memutuskan bahwa variabel apa pun yang sebenarnya didefinisikan dalam antarmuka adalah konstanta antarmuka.
pyrocrasty
6
Antarmuka tidak dapat memiliki variabel instan untuk menghindari pewarisan berganda masalah negara. Lihat docs.oracle.com/javase/tutorial/java/IandI/… . Kelas tidak dapat diperpanjang lebih dari satu kelas karena alasan yang sama.
denis
1
Bagaimana metode default diperkenalkan dan mereka memiliki instance, namun variabel instance tidak didukung ...
M.kazem Akhgary
41
Karena antarmuka tidak memiliki objek langsung, satu-satunya cara untuk mengaksesnya adalah dengan menggunakan kelas / antarmuka dan karenanya itulah mengapa jika variabel antarmuka ada, itu harus statis jika tidak dapat diakses sama sekali ke dunia luar. Sekarang karena ini statis, ia hanya dapat menampung satu nilai dan setiap kelas yang mengimplementasikannya dapat mengubahnya dan karenanya semuanya akan berantakan.
Oleh karena itu jika ada variabel antarmuka, itu akan secara implisit statis, final dan jelas bersifat publik !!!
Tentu saja variabel instan akan dapat diakses jika diizinkan dalam Java interface. Kelas akan mengimplementasikan antarmuka, mendeklarasikan variabel instance (seperti yang dipersyaratkan oleh antarmuka). Konstruktornya (atau metode lain) menetapkan variabel instan. Ketika sebuah instance dari kelas dipakai, Anda akan dapat mengakses variabel instance-nya.
pyrocrasty
Java memungkinkan metode statis dengan tubuh ada di antarmuka. Mereka dapat mengakses variabel statis. Mereka tidak dapat mengubahnya, yang berarti fungsi statis tidak dapat menyimpan data apa pun
sederhana
36
publik : untuk aksesibilitas di semua kelas, sama seperti metode yang ada di antarmuka
statis : karena antarmuka tidak dapat memiliki objek, interfaceName.variableName dapat digunakan untuk referensi atau langsung variabelName di kelas yang mengimplementasikannya.
final : untuk menjadikannya konstanta. Jika 2 kelas mengimplementasikan antarmuka yang sama dan Anda memberi keduanya hak untuk mengubah nilai, konflik akan terjadi pada nilai saat ini dari var, itulah sebabnya mengapa hanya satu kali inisialisasi diizinkan.
Juga semua pengubah ini tersirat untuk antarmuka, Anda tidak perlu menentukan salah satu dari mereka.
( Ini bukan jawaban filosofis tetapi lebih dari jawaban praktis ). Persyaratan untuk staticpengubah jelas yang telah dijawab oleh orang lain. Pada dasarnya, karena antarmuka tidak dapat dipakai, satu-satunya cara untuk mengakses bidangnya adalah menjadikannya bidang kelas - static.
Alasan di balik interfacebidang secara otomatis menjadi final(konstan) adalah untuk mencegah implementasi yang berbeda secara tidak sengaja mengubah nilai variabel antarmuka yang secara tidak sengaja dapat mempengaruhi perilaku implementasi lainnya. Bayangkan skenario di bawah ini di mana sebuah interfaceproperti tidak secara eksplisit menjadi finaloleh Java:
publicinterfaceActionable{publicstaticboolean isActionable =false;publicvoid performAction();}publicNuclearActionimplementsActionable{publicvoid performAction(){// Code that depends on isActionable variableif(isActionable){// Launch nuclear weapon!!!}}}
Sekarang, coba pikirkan apa yang akan terjadi jika kelas lain yang mengimplementasikan Actionablemengubah keadaan variabel antarmuka:
publicCleanActionimplementsActionable{publicvoid performAction(){// Code that can alter isActionable state since it is not constant
isActionable =true;}}
Jika kelas-kelas ini dimuat dalam JVM tunggal oleh classloader, maka perilaku NuclearActiondapat dipengaruhi oleh kelas lain CleanAction,, ketika performAction()dipanggil setelahCleanAction dieksekusi (di utas yang sama atau sebaliknya), yang dalam hal ini dapat menjadi bencana (semantik itu).
Karena kita tidak tahu bagaimana setiap implementasi interfaceakan menggunakan variabel-variabel ini, mereka harus secara implisit final.
Untuk menunjukkan bahwa ini adalah konstan. Java tidak memiliki kata kunci const. final statis adalah bagaimana Anda mendeklarasikan konstanta.
Amir Afghani
5
Karena Java 8, mereka dapat berisi implementasi, tetapi sangat disarankan untuk tidak menggunakannya jika Anda tidak memerlukan kompatibilitas backwarts. :)
codepleb
6
publicinterface A{int x=65;}publicinterface B{int x=66;}publicclass D implements A,B {publicstaticvoid main(String[] a){System.out.println(x);// which x?}}
Ini solusinya.
System.out.println(A.x);// done
Saya pikir itu adalah salah satu alasan mengapa variabel antarmuka statis.
Jangan mendeklarasikan variabel di dalam Antarmuka.
Bahkan, tanpa spesifikasi "Axe" bahkan tidak dapat dikompilasi ", sehingga sebenarnya aman untuk menggunakan variabel (yang secara implisit adalah final statis publik) dalam antarmuka.
Marco
Saya tidak setuju dengan jawabannya, seperti @Marco mengatakan itu bahkan tidak dapat dikompilasi. Saya tidak menemukan kelemahan lain sejauh ini, mungkin hanya karena Anda tidak melihat tulisan static finalsebelum variabel yang sebenarnya statis dan final.
Micer
5
statis - karena Antarmuka tidak dapat memiliki instance. dan final - karena kita tidak perlu mengubahnya.
"kami tidak perlu" == "kami tidak diizinkan", jangan campur artinya.
peterh
3
karena:
Static : karena kita tidak dapat memiliki objek antarmuka sehingga kita harus menghindari menggunakan variabel anggota tingkat objek dan harus menggunakan variabel tingkat kelas yaitu statis.
Final : agar kita tidak memiliki nilai ambigu untuk variabel (masalah Diamond - Multiple Inheritance).
Dan sesuai antarmuka dokumentasi adalah kontrak dan bukan implementasi.
Java tidak mengizinkan variabel abstrak dan / atau definisi konstruktor dalam antarmuka. Solusi: Cukup gantung kelas abstrak antara antarmuka Anda dan implementasi Anda yang hanya memperluas kelas abstrak seperti:
publicinterfaceIMyClass{void methodA();String methodB();Integer methodC();}publicabstractclass myAbstractClass implementsIMyClass{protectedString varA, varB;//Constructor
myAbstractClass(String varA,String varB){this.varA = varA;this.varB =VarB;}//Implement (some) interface methods here or leave them for the concrete classprotectedvoid methodA(){//Do something}//Add additional methods here which must be implemented in the concrete classprotectedabstractLong methodD();//Write some completely new methods which can be used by all subclassesprotectedFloat methodE(){return42.0;}}publicclass myConcreteClass extends myAbstractClass {//Constructor must now be implemented!
myClass(String varA,String varB){super(varA, varB);}//All non-private variables from the abstract class are available here//All methods not implemented in the abstract class must be implemented here}
Anda juga dapat menggunakan kelas abstrak tanpa antarmuka apa pun jika Anda PASTI bahwa Anda tidak ingin mengimplementasikannya bersama dengan antarmuka lain nanti. Harap dicatat bahwa Anda tidak dapat membuat instance dari kelas abstrak yang Anda HARUS memperpanjangnya terlebih dahulu.
(Kata kunci "dilindungi" berarti bahwa hanya kelas yang diperluas yang dapat mengakses metode dan variabel ini.)
Dalam antarmuka, variabel secara default ditetapkan oleh publik, statis, pengubah akses akhir . Karena:
publik: Terjadi beberapa kali antarmuka mungkin ditempatkan di beberapa paket lain. Jadi itu perlu mengakses variabel dari mana saja di proyek.
statis: Karena kelas tidak lengkap seperti itu tidak dapat membuat objek. Jadi dalam proyek kita perlu mengakses variabel tanpa objek sehingga kita dapat mengakses dengan bantuaninterface_filename.variable_name
final: Misalkan satu antarmuka mengimplementasikan oleh banyak kelas dan semua kelas mencoba mengakses dan memperbarui variabel antarmuka. Jadi itu mengarah pada tidak konsistennya mengubah data dan mempengaruhi setiap kelas lainnya. Jadi perlu mendeklarasikan pengubah akses dengan final.
Di Java , antarmuka tidak memungkinkan Anda untuk mendeklarasikan variabel instan apa pun. Menggunakan variabel yang dideklarasikan dalam antarmuka sebagai variabel instan akan mengembalikan kesalahan waktu kompilasi.
Anda bisa mendeklarasikan variabel konstan, menggunakan static finalyang berbeda dari variabel instan.
Ini jelas salah. Kompiler tidak akan mengeluh kecuali jika Anda membuatnya pribadi atau dilindungi. Di bawah tenda, seperti yang telah disebutkan orang lain, mereka dikonversi ke final statis publik. Dan saya kira itu sudah jelas mengapa. Karena antarmuka dimaksudkan untuk menentukan perilaku, bukan menyatakan.
Mikayil Abdullayev
0
Antarmuka dapat diimplementasikan oleh kelas apa saja dan bagaimana jika nilai itu diubah oleh salah satu kelas pelaksana di sana maka akan ada menyesatkan untuk kelas pelaksana lainnya. Antarmuka pada dasarnya adalah referensi untuk menggabungkan dua entitas yang saling berhubungan tetapi berbeda. Oleh karena itu, variabel yang mendeklarasikan di dalam antarmuka secara implisit bersifat final dan juga statis karena antarmuka tidak dapat dibuat instantiate.
Pikirkan aplikasi web tempat antarmuka Anda ditentukan dan kelas lain mengimplementasikannya. Karena Anda tidak dapat membuat instance antarmuka untuk mengakses variabel, Anda harus memiliki kata kunci statis. Karena sifatnya statis setiap perubahan nilai akan mencerminkan ke instance lain yang telah menerapkannya. Jadi untuk mencegahnya kita mendefinisikannya sebagai final.
Baru saja dicoba di Eclipse, variabel dalam antarmuka default menjadi final, jadi Anda tidak dapat mengubahnya. Dibandingkan dengan kelas induk, variabelnya pasti dapat diubah. Mengapa? Dari poin saya, variabel di kelas adalah atribut yang akan diwarisi oleh anak-anak, dan anak-anak dapat mengubahnya sesuai dengan kebutuhan mereka yang sebenarnya. Sebaliknya, antarmuka hanya mendefinisikan perilaku, bukan atribut. Satu-satunya alasan untuk memasukkan variabel dalam antarmuka adalah untuk menggunakannya sebagai const yang terkait dengan antarmuka itu. Padahal, ini bukan praktik yang baik menurut kutipan berikut:
"Menempatkan konstanta dalam antarmuka adalah teknik yang populer di masa-masa awal Jawa, tetapi sekarang banyak yang menganggapnya sebagai penggunaan antarmuka yang tidak menyenangkan, karena antarmuka harus berurusan dengan layanan yang disediakan oleh objek, bukan datanya. Juga, konstanta yang digunakan oleh sebuah kelas biasanya merupakan detail implementasi, tetapi menempatkannya di antarmuka mempromosikannya ke API publik dari kelas tersebut. "
Saya juga mencoba menempatkan statis atau tidak ada bedanya sama sekali. Kodenya seperti di bawah ini:
Jawaban:
Dari FAQ desain antarmuka Java oleh Philip Shaw:
sumber
sumber
static
pengubah ini sepenuhnya palsu. Variabel instance publik kelas adalah bagian dari antarmuka dan tidak ada alasan mengapa mereka tidak boleh diabstraksi dalam Javainterface
, sama seperti metode instance. Tidak masalah bahwa Javainterface
tidak dapat di-instantiated secara langsung - Anda masih dapat memiliki instance kelas yang mengimplementasikannyainterface
dan masuk akal untuk mengharuskan mereka memiliki variabel instance publik tertentu. Adapun bagian tentangfinal
, itu tidak menawarkan penjelasan sama sekali - itu hanya menjelaskan apafinal
artinya.Karena antarmuka tidak memiliki objek langsung, satu-satunya cara untuk mengaksesnya adalah dengan menggunakan kelas / antarmuka dan karenanya itulah mengapa jika variabel antarmuka ada, itu harus statis jika tidak dapat diakses sama sekali ke dunia luar. Sekarang karena ini statis, ia hanya dapat menampung satu nilai dan setiap kelas yang mengimplementasikannya dapat mengubahnya dan karenanya semuanya akan berantakan.
Oleh karena itu jika ada variabel antarmuka, itu akan secara implisit statis, final dan jelas bersifat publik !!!
sumber
interface
. Kelas akan mengimplementasikan antarmuka, mendeklarasikan variabel instance (seperti yang dipersyaratkan oleh antarmuka). Konstruktornya (atau metode lain) menetapkan variabel instan. Ketika sebuah instance dari kelas dipakai, Anda akan dapat mengakses variabel instance-nya.publik : untuk aksesibilitas di semua kelas, sama seperti metode yang ada di antarmuka
statis : karena antarmuka tidak dapat memiliki objek, interfaceName.variableName dapat digunakan untuk referensi atau langsung variabelName di kelas yang mengimplementasikannya.
final : untuk menjadikannya konstanta. Jika 2 kelas mengimplementasikan antarmuka yang sama dan Anda memberi keduanya hak untuk mengubah nilai, konflik akan terjadi pada nilai saat ini dari var, itulah sebabnya mengapa hanya satu kali inisialisasi diizinkan.
Juga semua pengubah ini tersirat untuk antarmuka, Anda tidak perlu menentukan salah satu dari mereka.
sumber
( Ini bukan jawaban filosofis tetapi lebih dari jawaban praktis ). Persyaratan untuk
static
pengubah jelas yang telah dijawab oleh orang lain. Pada dasarnya, karena antarmuka tidak dapat dipakai, satu-satunya cara untuk mengakses bidangnya adalah menjadikannya bidang kelas -static
.Alasan di balik
interface
bidang secara otomatis menjadifinal
(konstan) adalah untuk mencegah implementasi yang berbeda secara tidak sengaja mengubah nilai variabel antarmuka yang secara tidak sengaja dapat mempengaruhi perilaku implementasi lainnya. Bayangkan skenario di bawah ini di mana sebuahinterface
properti tidak secara eksplisit menjadifinal
oleh Java:Sekarang, coba pikirkan apa yang akan terjadi jika kelas lain yang mengimplementasikan
Actionable
mengubah keadaan variabel antarmuka:Jika kelas-kelas ini dimuat dalam JVM tunggal oleh classloader, maka perilaku
NuclearAction
dapat dipengaruhi oleh kelas lainCleanAction
,, ketikaperformAction()
dipanggil setelahCleanAction
dieksekusi (di utas yang sama atau sebaliknya), yang dalam hal ini dapat menjadi bencana (semantik itu).Karena kita tidak tahu bagaimana setiap implementasi
interface
akan menggunakan variabel-variabel ini, mereka harus secara implisitfinal
.sumber
Karena hal lain adalah bagian dari implementasi, dan antarmuka tidak dapat memuat implementasi apa pun.
sumber
Ini solusinya.
Saya pikir itu adalah salah satu alasan mengapa variabel antarmuka statis.
Jangan mendeklarasikan variabel di dalam Antarmuka.
sumber
static final
sebelum variabel yang sebenarnya statis dan final.statis - karena Antarmuka tidak dapat memiliki instance. dan final - karena kita tidak perlu mengubahnya.
sumber
karena:
Static
: karena kita tidak dapat memiliki objek antarmuka sehingga kita harus menghindari menggunakan variabel anggota tingkat objek dan harus menggunakan variabel tingkat kelas yaitu statis.Final
: agar kita tidak memiliki nilai ambigu untuk variabel (masalah Diamond - Multiple Inheritance).Dan sesuai antarmuka dokumentasi adalah kontrak dan bukan implementasi.
referensi: Jawaban Abhishek Jain tentang quora
sumber
Java tidak mengizinkan variabel abstrak dan / atau definisi konstruktor dalam antarmuka. Solusi: Cukup gantung kelas abstrak antara antarmuka Anda dan implementasi Anda yang hanya memperluas kelas abstrak seperti:
Anda juga dapat menggunakan kelas abstrak tanpa antarmuka apa pun jika Anda PASTI bahwa Anda tidak ingin mengimplementasikannya bersama dengan antarmuka lain nanti. Harap dicatat bahwa Anda tidak dapat membuat instance dari kelas abstrak yang Anda HARUS memperpanjangnya terlebih dahulu.
(Kata kunci "dilindungi" berarti bahwa hanya kelas yang diperluas yang dapat mengakses metode dan variabel ini.)
spyro
sumber
Antarmuka adalah kontrak antara dua pihak yang invarian, diukir di batu, karenanya final. Lihat Desain dengan Kontrak .
sumber
Antarmuka: Layanan persyaratan sistem.
Dalam antarmuka, variabel secara default ditetapkan oleh publik, statis, pengubah akses akhir . Karena:
publik: Terjadi beberapa kali antarmuka mungkin ditempatkan di beberapa paket lain. Jadi itu perlu mengakses variabel dari mana saja di proyek.
statis: Karena kelas tidak lengkap seperti itu tidak dapat membuat objek. Jadi dalam proyek kita perlu mengakses variabel tanpa objek sehingga kita dapat mengakses dengan bantuan
interface_filename.variable_name
final: Misalkan satu antarmuka mengimplementasikan oleh banyak kelas dan semua kelas mencoba mengakses dan memperbarui variabel antarmuka. Jadi itu mengarah pada tidak konsistennya mengubah data dan mempengaruhi setiap kelas lainnya. Jadi perlu mendeklarasikan pengubah akses dengan final.
sumber
Di
Java
, antarmuka tidak memungkinkan Anda untuk mendeklarasikan variabel instan apa pun. Menggunakan variabel yang dideklarasikan dalam antarmuka sebagai variabel instan akan mengembalikan kesalahan waktu kompilasi.Anda bisa mendeklarasikan variabel konstan, menggunakan
static final
yang berbeda dari variabel instan.sumber
Antarmuka dapat diimplementasikan oleh kelas apa saja dan bagaimana jika nilai itu diubah oleh salah satu kelas pelaksana di sana maka akan ada menyesatkan untuk kelas pelaksana lainnya. Antarmuka pada dasarnya adalah referensi untuk menggabungkan dua entitas yang saling berhubungan tetapi berbeda. Oleh karena itu, variabel yang mendeklarasikan di dalam antarmuka secara implisit bersifat final dan juga statis karena antarmuka tidak dapat dibuat instantiate.
sumber
Pikirkan aplikasi web tempat antarmuka Anda ditentukan dan kelas lain mengimplementasikannya. Karena Anda tidak dapat membuat instance antarmuka untuk mengakses variabel, Anda harus memiliki kata kunci statis. Karena sifatnya statis setiap perubahan nilai akan mencerminkan ke instance lain yang telah menerapkannya. Jadi untuk mencegahnya kita mendefinisikannya sebagai final.
sumber
Baru saja dicoba di Eclipse, variabel dalam antarmuka default menjadi final, jadi Anda tidak dapat mengubahnya. Dibandingkan dengan kelas induk, variabelnya pasti dapat diubah. Mengapa? Dari poin saya, variabel di kelas adalah atribut yang akan diwarisi oleh anak-anak, dan anak-anak dapat mengubahnya sesuai dengan kebutuhan mereka yang sebenarnya. Sebaliknya, antarmuka hanya mendefinisikan perilaku, bukan atribut. Satu-satunya alasan untuk memasukkan variabel dalam antarmuka adalah untuk menggunakannya sebagai const yang terkait dengan antarmuka itu. Padahal, ini bukan praktik yang baik menurut kutipan berikut:
"Menempatkan konstanta dalam antarmuka adalah teknik yang populer di masa-masa awal Jawa, tetapi sekarang banyak yang menganggapnya sebagai penggunaan antarmuka yang tidak menyenangkan, karena antarmuka harus berurusan dengan layanan yang disediakan oleh objek, bukan datanya. Juga, konstanta yang digunakan oleh sebuah kelas biasanya merupakan detail implementasi, tetapi menempatkannya di antarmuka mempromosikannya ke API publik dari kelas tersebut. "
Saya juga mencoba menempatkan statis atau tidak ada bedanya sama sekali. Kodenya seperti di bawah ini:
sumber