Perbedaan variabel anggota statis dan variabel anggota non statis
Ambil contoh berikut sebagai contoh
paket cn.galc.test;public class Cat { /** * Variabel anggota statis*/ private static int sid = 0; private String name; } public void info() { System.out.println("Nama Saya adalah " + nama + ",TIDAK." + id); public static void main(String[] args) { Cat.sid = 100; Kucing mimi = Kucing baru("mimi"); Kucing pipi = Kucing baru("pipi");Pahami proses eksekusi seluruh program dengan menggambar diagram analisis memori
Saat mengeksekusi kalimat pertama program: Cat.sid = 100;, sid di sini adalah variabel anggota statis. Variabel statis disimpan di area data (seg data), jadi alokasikan terlebih dahulu ruang kecil sid di area data .Setelah kalimat dieksekusi, sid berisi nilai 100.
Diagram tata letak memori saat ini adalah sebagai berikut:
Selanjutnya, program dijalankan:
Kucing mimi = Kucing baru(“mimi”);
Di sini, metode konstruktor Cat(Nama string) dari kelas Cat dipanggil. Metode konstruktor didefinisikan sebagai berikut:
Kucing (String nama){ this.name = nama; id=sid++ } Saat memanggil, pertama-tama alokasikan sebagian kecil memori mm di memori tumpukan, yang berisi alamat objek instance kelas Cat di memori heap mm adalah objek referensi objek kelas Cat di memori heap. Konstruktor ini mendeklarasikan variabel parameter formal bertipe string, jadi "mimi" diteruskan ke konstruktor sebagai parameter aktual Karena konstanta string dialokasikan dan disimpan di area data, ada sedikit memori ekstra di area data . Digunakan untuk menyimpan string "mimi". Distribusi memori saat ini ditunjukkan pada gambar di bawah ini:
Saat memanggil konstruktor, pertama-tama alokasikan ruang kecil di memori tumpukan untuk nama parameter formal, lalu teruskan string "mimi" sebagai parameter aktual ke nama. String tersebut juga merupakan tipe referensi, kecuali Kecuali untuk empat dan delapan tipe data dasar, yang lainnya adalah tipe referensi, sehingga dapat dianggap bahwa string juga merupakan objek. Jadi ini setara dengan meneruskan referensi objek "mimi" ke nama, jadi sekarang nama menunjuk ke "mimi". Jadi layout memori saat ini adalah seperti gambar di bawah ini:
Selanjutnya, jalankan kode di badan konstruktor:
ini.nama=nama;
Ini di sini mengacu pada objek saat ini, yang merujuk pada kucing di memori heap. Di sini, nilai yang terkandung dalam nama di tumpukan diteruskan ke atribut nama objek cat di memori heap, jadi saat ini nilai yang terkandung dalam nama juga dapat ditemukan di objek string "mimi" yang terletak di Area data. Saat ini, nama ini juga merupakan objek referensi dari objek string "mimi". Melalui nilai atributnya, objek string "mimi" yang terletak di area data dapat ditemukan. Distribusi memori saat ini ditunjukkan pada gambar di bawah ini:
Selanjutnya, jalankan baris kode lain di badan metode:
id=sid++;
Disini nilai sid diteruskan ke id, sehingga nilai id adalah 100. Setelah sid dilewatkan, tambahkan 1. Saat ini sid menjadi 101. Tata letak memori saat ini ditunjukkan pada gambar di bawah.
Pada titik ini, metode konstruktor dipanggil, dan semua ruang memori yang ditempati oleh variabel lokal yang dialokasikan untuk metode konstruktor ini akan hilang, sehingga memori nama yang terletak di ruang tumpukan akan hilang. Referensi ke objek string "mimi" di area data di memori tumpukan juga hilang. Saat ini, hanya referensi ke objek string "mimi" di memori heap yang tersisa. Tata letak memori saat ini adalah seperti yang ditunjukkan di bawah ini:
Selanjutnya jalankan:
Kucing pipi = Kucing baru("pipi"); Berikut adalah pemanggilan kedua ke metode konstruktor Cat(). Seluruh proses pemanggilan sama seperti pemanggilan pertama kali, tata letak memori saat ini adalah seperti yang ditunjukkan pada gambar di bawah ini:
Dua baris kode terakhir dicetak dengan memanggil metode info(). Hasil pencetakannya adalah sebagai berikut:
Melalui program ini kita dapat melihat peran sid variabel anggota statis ini yang dapat dihitung. Setiap kali kucing baru keluar, berikan nomornya. Biarkan ia menambahkan 1 dengan sendirinya.
Setelah program dijalankan, seluruh layout yang ada di memori akan seperti terlihat pada gambar di atas. Berlanjut hingga saat sebelum pemanggilan metode utama selesai.
Di sini, metode konstruktor Cat(Nama string) dipanggil untuk membuat dua kucing. Pertama, dua spasi kecil, mimi dan pipi, dialokasikan dalam memori tumpukan, yang berisi alamat di mana kedua kucing tersebut dapat ditemukan ke alamat di memori heap. Dua tanda kutip kucing. Metode konstruksi di sini mendeklarasikan variabel bertipe string. Konstanta string dialokasikan di area data, sehingga string mimi dan pipi yang diteruskan akan disimpan di area data. Oleh karena itu, area data dialokasikan dua blok kecil memori untuk menyimpan string mimi dan pipi, yang berisi string "mimi" dan "pipi". String juga merupakan tipe referensi Semua tipe data adalah tipe referensi. Jadi Anda bisa menganggap string sebagai sebuah objek.
Berikut adalah dua kucing baru. Kedua kucing tersebut memiliki atribut id dan name masing-masing, jadi id dan name di sini adalah variabel anggota non-statis, yaitu tidak ada modifikasi statis. Jadi setiap kali kucing baru dibuat, kucing baru ini memiliki id dan namanya sendiri, yaitu variabel anggota non-statis id dan nama memiliki salinan terpisah untuk setiap objek. Namun untuk variabel anggota statis, hanya ada satu salinan. Tidak peduli berapa banyak objek baru, meskipun tidak ada objek baru, variabel anggota statis akan menyimpan satu salinan di area data. Seperti sid di sini, sid disimpan di area data. Tidak peduli berapa banyak kucing baru yang ada di memori heap, hanya ada satu salinan sid, dan hanya satu salinan yang disimpan di area data.
Variabel anggota statis adalah milik seluruh kelas, bukan milik objek tertentu. Jadi bagaimana cara mengakses nilai variabel anggota statis ini? Pertama-tama, objek apa pun dapat mengakses nilai statis ini, dan saat mengakses, objek tersebut mengakses memori yang sama. Poin kedua adalah Anda dapat mengakses nilai statis ini meskipun tidak ada objek. Anda dapat mengakses nilai statis ini melalui "nama kelas.nama variabel anggota statis", sehingga di masa mendatang Anda akan melihat nama kelas tertentu ditambah "." diikuti dengan Jika ada satu hal, maka hal berikutnya harus statis, misalnya "Sistem.out". Di sini, keluar ini diakses melalui nama kelas (kelas Sistem) ditambah ".", jadi keluar ini harus statis.
Jika anggota kelas dinyatakan statis, ia dapat diakses sebelum objek apa pun di kelas tersebut dibuat tanpa harus mereferensikan objek apa pun. Contoh paling umum dari anggota statis adalah main(). Karena main() harus dipanggil ketika program mulai dieksekusi, maka program tersebut dinyatakan statis.
Variabel yang dinyatakan statis pada dasarnya adalah variabel global. Ketika suatu objek dideklarasikan, salinan variabel statis tidak dihasilkan, tetapi semua variabel instan dari kelas tersebut berbagi variabel statis yang sama. Misalnya: mendeklarasikan jumlah variabel statis sebagai jumlah instance kelas baru. Metode yang dinyatakan statis memiliki batasan sebagai berikut:
(1). Mereka hanya dapat memanggil metode statis lainnya.
(2) Mereka hanya dapat mengakses data statis.
(3). Mereka tidak dapat merujuk ini atau super dengan cara apa pun.
Jika Anda perlu menginisialisasi variabel statis melalui penghitungan, Anda dapat mendeklarasikan blok statis. Blok Statis hanya dijalankan satu kali saat kelas dimuat. Contoh di bawah ini menunjukkan
Kelas memiliki metode statis, beberapa variabel statis, dan blok inisialisasi statis: public class UserStatic { static int a = 3; static int b; static void meth(int x) { System.out.println("x = " + x); System.out.println("a = " + a); System.out.println("b = " + b); static { System.out.println("Blok statis diinisialisasi."); b = a * 4; } public static void main(String args[]) { meth(42); } } Setelah kelas UseStatic dimuat, semua pernyataan statis dijalankan. Pertama, a diatur ke 3, kemudian blok statis dieksekusi (mencetak pesan), dan terakhir, b diinisialisasi ke a*4 atau 12. Kemudian main() dipanggil, main() memanggil meth(), meneruskan nilai 42 ke x. Tiga pernyataan println() mengacu pada dua variabel statis a dan b, dan variabel lokal x.
Catatan: Mereferensikan variabel instan apa pun dalam metode statis adalah tindakan ilegal.
Berikut adalah output dari program ini:
Blok statis diinisialisasi x = 42 a = 3 b = 12
Metode dan variabel statis dapat digunakan secara independen dari objek apa pun di luar kelas tempat mereka didefinisikan. Dalam hal ini, Anda hanya perlu menambahkan operator titik (.) setelah nama kelas. Misalnya, jika Anda ingin memanggil metode statis dari luar kelas, Anda bisa menggunakan format umum berikut:
nama kelas.metode()
Di sini, nama kelas adalah nama kelas di mana metode statis didefinisikan. Seperti yang Anda lihat, format ini mirip dengan format pemanggilan metode non-statis melalui variabel referensi objek. Variabel statis dapat diakses dalam format yang sama - nama kelas ditambah operator titik. Beginilah cara Java mengimplementasikan versi fungsi global dan variabel global yang terkontrol.
Meringkaskan:
(1) Anggota statis tidak dapat diakses oleh instance yang dibuat oleh kelas di mana mereka berada.
(2) Jika anggota tanpa modifikasi statis adalah anggota objek, maka mereka dimiliki oleh masing-masing objek.
(3) Anggota yang dimodifikasi dengan statis adalah anggota kelas, yang dapat langsung dipanggil oleh suatu kelas dan bersifat umum untuk semua objek.
Java Static: Sebagai pengubah, dapat digunakan untuk mengubah variabel, metode, dan blok kode (tetapi tidak boleh mengubah kelas).
(1) Ubah variabel:
Properti yang dimiliki bersama oleh semua objek suatu kelas, juga disebut variabel kelas. Ini mirip dengan variabel global dalam bahasa C. Variabel kelas diinisialisasi ketika kelas dimuat dan hanya diinisialisasi satu kali. Ketika objek apa pun dalam program memodifikasi variabel statis, objek lain akan melihat nilai yang dimodifikasi. Jadi variabel kelas dapat digunakan sebagai counter. Selain itu, variabel Java Static dapat diakses langsung menggunakan nama kelas tanpa memerlukan objek.
(2) Metode modifikasi:
Fungsi yang umum untuk semua objek suatu kelas disebut metode statis. Metode statis juga dapat diakses langsung menggunakan nama kelas, tanpa memerlukan objek. Oleh karena itu, variabel non-statis dan metode non-statis tidak dapat diakses langsung dalam metode statis, dan kata kunci seperti ini atau super tidak dapat muncul dalam metode Statis.
(3) Ubah blok kode Java:
Gunakan statis untuk mengubah blok kode independen di kelas, yang disebut blok kode statis. Blok kode statis dieksekusi ketika kelas dimuat untuk pertama kalinya, dan hanya sekali. Blok kode statis tidak memiliki nama, sehingga tidak dapat dipanggil secara eksplisit, tetapi hanya dipanggil oleh mesin virtual saat kelas dimuat. Ini terutama digunakan untuk menyelesaikan beberapa operasi inisialisasi.
(4) Mari kita bicara tentang pemuatan kelas:
Saat JVM menggunakan suatu kelas untuk pertama kalinya, ia akan menuju ke jalur yang ditentukan oleh classpath untuk menemukan file bytecode yang sesuai dengan kelas tersebut, dan membacanya ke dalam JVM dan menyimpannya.
Terlihat apakah itu variabel, metode, atau blok kode, asalkan dimodifikasi dengan statis, maka akan "siap" ketika kelas dimuat, yaitu dapat digunakan atau telah dieksekusi. Semua bisa dieksekusi tanpa objek. Sebaliknya jika tidak ada statis maka harus diakses melalui objek.