Java基礎(chǔ)教程之static五大應(yīng)用場(chǎng)景
前言
static和final是兩個(gè)我們必須掌握的關(guān)鍵字。不同于其他關(guān)鍵字,他們都有多種用法,而且在一定環(huán)境下使用,可以提高程序的運(yùn)行性能,優(yōu)化程序的結(jié)構(gòu)。上一個(gè)章節(jié)我們講了final關(guān)鍵字的原理及用法,本章節(jié)我們來(lái)了解一下static關(guān)鍵字原理及其用法。
一. static特點(diǎn)
static是一個(gè)修飾符,通常用于修飾變量和方法,如開(kāi)發(fā)過(guò)程中用到的字典類數(shù)據(jù)都會(huì)用到static來(lái)修飾,工具類方法,如Dateutils,Stringutils這類工具方法也會(huì)用到static來(lái)修飾,那么除了這兩種最常用的場(chǎng)景外,是否還有其他場(chǎng)景呢,答案是:有的,總共五種:
- static變量
- static方法
- static代碼塊
- static內(nèi)部類
- static包內(nèi)導(dǎo)入
static修飾的變量、方法、代碼塊、內(nèi)部類在類加載期間就已經(jīng)完成初始化,存儲(chǔ)在Java Heap(JDK7.0之前存儲(chǔ)在方法區(qū))中靜態(tài)存儲(chǔ)區(qū),因此static優(yōu)于對(duì)象而存在。
static修飾的成員(變量、方法)被所有對(duì)象所共享,也叫靜態(tài)變量或靜態(tài)方法,可直接通過(guò)類調(diào)用(也建議通過(guò)類調(diào)用)。
二. static 變量
static變量隨著類的加載而存在,隨著類的消失而消失,當(dāng)類被加載時(shí),就會(huì)為靜態(tài)變量在Java Heap中分配內(nèi)存空間,可以通過(guò)【類.變量名】和【對(duì)象.變量名】的方式調(diào)用,建議直接使用【類.變量名】的方式,
public class Person {
private String name;
private static int eyeNum;
public static int legNum = 2;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public static int getEyeNum() {
return eyeNum;
}
public static void setEyeNum(int eyeNum) {
Person.eyeNum = eyeNum;
}
}
public static void main(String[] args) {
Person person = new Person();
person.setEyeNum(25);
Person person1 = new Person();
person1.setEyeNum(28);
System.out.println(person.getEyeNum());//28
System.out.println(person1.getEyeNum());//28
int legNum = person.legNum;
System.out.println(legNum);//2
}
從上面的例子可以看出靜態(tài)變量是對(duì)所有對(duì)象共享,一個(gè)對(duì)象對(duì)其值的改動(dòng),直接就會(huì)造成另一個(gè)對(duì)象取值的不同。
什么時(shí)候使用static變量?
作為共享變量使用,通常搭配final關(guān)鍵字一起使用,比如我們常用的字典類數(shù)據(jù);
private static final String GENERAL_MAN = "man";
減少對(duì)象的創(chuàng)建,比如在類開(kāi)頭的部分,定義Logger方法,用于異常日志采集
private static Logger LOGGER = LogFactory.getLoggger(MyClass.class);
始終返回同一變量,比如我們的單例模式。
三. static 方法
靜態(tài)方法只能訪問(wèn)靜態(tài)成員(靜態(tài)變量、靜態(tài)方法),而非靜態(tài)方法既可訪問(wèn)靜態(tài)方法也可訪問(wèn)非靜態(tài)方法;因?yàn)殪o態(tài)成員優(yōu)于對(duì)象而存在,因此無(wú)法調(diào)用和對(duì)象相關(guān)的關(guān)鍵字,如this,super,無(wú)法通過(guò)關(guān)鍵字訪問(wèn)對(duì)象資源。
public class Person {
private String name;
private static int eyeNum;
public static int legNum = 2;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public static int getEyeNum() {
System.out.println(name);//編譯出錯(cuò),name不可用
return eyeNum;
}
public static void setEyeNum(int eyeNum) {
Person.eyeNum = eyeNum;
this.name = "";//編譯出錯(cuò),this不可用
}
}
什么時(shí)候使用static方法?
static方法一般用于與當(dāng)前對(duì)象無(wú)法的工廠方法、工具方法。如Math.sqrt(),Arrays.sort(),StringUtils.isEmpty()等。
四. static 代碼塊
static代碼塊相對(duì)于static變量和static方法來(lái)說(shuō)使用不是那么廣泛,但也算是比較常見(jiàn)的用法了,static代碼塊在加載一個(gè)類的時(shí)候最先執(zhí)行,且只執(zhí)行一次。
public static Map<String, String> timeTypes;
static {
timeTypes = new HashMap<>();
timeTypes.put("year", "年");
timeTypes.put("quarter", "季");
timeTypes.put("month", "月");
timeTypes.put("day", "日");
System.out.println("初始化1");
}
public static void main(String[] args) {
System.out.println("初始化2");
}
執(zhí)行結(jié)果是:
初始化1;
初始化2;
什么時(shí)候使用static代碼塊?
一般在進(jìn)行初始化操作時(shí),比如讀取配置文件信息,獲取當(dāng)前服務(wù)器參數(shù)等
五. static內(nèi)部類
定義一個(gè)內(nèi)部類,加上static,就成為了一個(gè)static內(nèi)部類,static只能修飾內(nèi)部類,不能修飾頂級(jí)類,靜態(tài)內(nèi)部類在業(yè)務(wù)應(yīng)用系統(tǒng)開(kāi)發(fā)中使用的不多。
public class StaticCouter {
private String str0 = "hi"; //非靜態(tài)變量
private static String str1 = "hello"; //靜態(tài)變量
static class StaticInnerClass{//靜態(tài)內(nèi)部類
public void getMessage(){
System.out.println(str0);//編譯出錯(cuò)
System.out.println(str1);
}
}
class NormalInnerClass{//非靜態(tài)內(nèi)部類
public void getMessage(){
System.out.println(str0);
System.out.println(str1);
}
}
}
靜態(tài)內(nèi)部類與非靜態(tài)內(nèi)部類有何異同?
| 靜態(tài)內(nèi)部類 | 非靜態(tài)內(nèi)部類 |
|---|---|
| 不需要有指向外部類的引用 | 必須通過(guò)外部類的new關(guān)鍵字引用 |
| 可定義普通變量和方法,也可定義靜態(tài)變量和方法 | 可定義普通變量和方法,不可定義靜態(tài)變量和方法 |
| 可以調(diào)用外部類的靜態(tài)成員,不能調(diào)用外部類的普通成員 | 可調(diào)用外部類的普通成員和靜態(tài)成員 |
public static void main(String[] args) {
//創(chuàng)建靜態(tài)內(nèi)部類實(shí)例
StaticInnerClass staticInnerClass = new StaticInnerClass();
//調(diào)用靜態(tài)內(nèi)部類方法
staticInnerClass.getMessage();
//創(chuàng)建靜態(tài)內(nèi)部類實(shí)例
StaticCouter.StaticInnerClass staticInnerClass1 = new staticCouter.StaticInnerClass();
//調(diào)用靜態(tài)內(nèi)部類方法
staticInnerClass1.getMessage();
//創(chuàng)建普通內(nèi)部類實(shí)例
StaticCouter.NormalInnerClass normalInnerClass = new StaticCouter().new NormalInnerClass();
//調(diào)用普通內(nèi)部類方法
normalInnerClass.getMessage();
}
六. static包內(nèi)導(dǎo)入
這個(gè)概念不太好理解,舉個(gè)例子
public static void main(String[] args) {
int[] arra = {1,4,5,7};
Arrays.sort(arra);
Arrays.asList(arra);
Arrays.fill(arra, 6);
}
static包導(dǎo)入目的就是去掉重復(fù)的Arrays類名調(diào)用
通過(guò)在頂部引入
import static java.util.Arrays.*
即可把Arrays類中所有的靜態(tài)變量,方法,內(nèi)部類等都引入當(dāng)前類中,調(diào)用時(shí)直接調(diào)用sort(arra),asList(arra),
java5后引入的,不常用,調(diào)用類方法時(shí)會(huì)比較簡(jiǎn)單,但可讀性不好,慎用。
七. 總結(jié)
static是java中很常用的一個(gè)關(guān)鍵字,使用場(chǎng)景也很多,本文主要介紹了它的五種用法,static變量,static方法,static代碼塊,static內(nèi)部類,static包內(nèi)導(dǎo)入,若有不對(duì)之處,請(qǐng)批評(píng)指正,望共同進(jìn)步,謝謝!
好了,以上就是這篇文章的全部?jī)?nèi)容了,希望本文的內(nèi)容對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,謝謝大家對(duì)腳本之家的支持。
相關(guān)文章
解決Springboot集成Redis集群配置公網(wǎng)IP連接報(bào)私網(wǎng)IP連接失敗問(wèn)題
在Springboot 集成 Redis集群配置公網(wǎng)IP連接報(bào)私網(wǎng)IP連接失敗,一直報(bào)私有IP連接失敗,所以本文小編給大家介紹了如何解決報(bào)錯(cuò)問(wèn)題,如果有遇到相同問(wèn)題的同學(xué),可以參考閱讀本文2023-10-10
淺析Java設(shè)計(jì)模式編程中的單例模式和簡(jiǎn)單工廠模式
這篇文章主要介紹了淺析Java設(shè)計(jì)模式編程中的單例模式和簡(jiǎn)單工廠模式,使用設(shè)計(jì)模式編寫代碼有利于團(tuán)隊(duì)協(xié)作時(shí)程序的維護(hù),需要的朋友可以參考下2016-01-01
Java的synchronized關(guān)鍵字深入解析
這篇文章主要介紹了Java的synchronized關(guān)鍵字深入解析,在并發(fā)編程中,多線程同時(shí)并發(fā)訪問(wèn)的資源叫做臨界資源,當(dāng)多個(gè)線程同時(shí)訪問(wèn)對(duì)象并要求操作相同資源時(shí),分割了原子操作就有可能出現(xiàn)數(shù)據(jù)的不一致或數(shù)據(jù)不完整的情況,需要的朋友可以參考下2023-12-12
springboot實(shí)現(xiàn)定時(shí)器(一看即會(huì),非常簡(jiǎn)單)
這篇文章主要介紹了springboot實(shí)現(xiàn)定時(shí)器(一看即會(huì),非常簡(jiǎn)單),具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2023-12-12

