配置java環境變量:
?? ?JAVA_HOME:配置JDK的目錄
?? ?CLASSPATH:指定到哪里去找運行時需要用到的類代碼(字節碼)
?? ?PATH:指定可執行程序的位置
?? ?
?? ?LINUX系統(在" .bash_profile "下的環境變量設置)
?? ??? ?JAVA_HOME=/opt/jdk1.5.0_06
?? ??? ?CLASSPATH=.:$JAVA_HOME/lib/tools.jar:$JAVA_HOME/lib/dt.jar
?? ??? ?PATH=$PATH:$JAVA_HOME/bin:.
?? ??? ?export JAVA_HOME CLASSPATH PATH???? (將指定的環境變量聲明為全局的)
?? ??? ??? ?
?? ?windows系統:
?? ??? ?右擊我的電腦-->屬性-->高級-->環境變量
?? ??? ?
Java的運行過程:
?? ?編譯:生成可執行文件,如C++中利用g++生成a.out,效率高,但不跨平臺
?? ?解釋:解釋器把源文件逐行解釋,跨平臺但效率不高
?? ?
?? ?在java中:先編譯后解釋,把.java文件編譯成.class字節碼文件
?? ??? ?Java源代碼文件(.java文件)--->
?? ??? ?Java編譯器(javac)--->
?? ??? ?Java字節碼文件(.class文件,平臺無關的)--->
?? ??? ?Java解釋器(java),執行Java字節碼
?
Java的垃圾回收:
?? ?由一個后臺線程gc進行垃圾回收
?? ?虛擬機判定內存不夠的時候會中斷代碼的運行,這時候gc才進行垃圾回收
?? ?缺點:不能夠精確的去回收內存
?? ?java.lang.System.gc();?? ?建議回收內存,但系統不一定回應,他會先去看內存是否夠用,夠用則不予理睬,不夠用才會去進行垃圾回收
?? ?內存中什么算是垃圾:
?? ??? ?不在被引用的對象(局部變量,沒有指針指向的)
?? ??? ?
java的安全性:
?? ?沙箱機制:只能做沙箱允許的操作
?? ?通過下面環節,實現安全
?? ??? ?加載有用的類文件,不需要的不加載
?? ??? ?校驗字節碼,查看允許的操作
?? ??? ??? ?查看代碼和虛擬機的特性是否相符
?? ??? ??? ?查看代碼是否有破壞性
?? ??? ??? ?查看是否有違規操作,如越界
?? ??? ??? ?查看類型是否匹配,類型轉換是否能正確執行
?? ??? ??? ?
源程序:
?? ?package mypack;?? ??? ?//相當于一個目錄
?? ?
?? ?public class HelloWorld{
?? ??? ?public static void main(String[] args){
?? ??? ??? ?System.out.println(“Hello World”); ?
?? ??? ?}
?? ?}
?? ?注:
?? ??? ?1、文件名必須和public修飾的類名一致,以.java作為文件后綴,如果定義的類不是public的,則文件名與類名可以不同。
?? ??? ?2、一個.java文件中可以有多個class,但是只有一個public修飾的類。
?? ??? ?3、java源代碼文件編譯后,一個類對應生成一個.class文件
?? ??? ?4、一個java應用程序應該包含一個main()方法,而且其簽名是固定的,它是應用程序的入口方法,可以定義在任意一個類中,不一定是public修飾的類
?? ??? ?編譯:javac -d . HelloWorld.java
?? ??? ??? ?含有包的類,在編譯的時候最好用上面的格式,-d指的是讓該類生成的時候按照包結構去生成," . "指的是在當前路徑下生成
?? ??? ??? ?如果不用上面的格式,也可以用javac HelloWorld.java,但是需要注意的是包結構就要由自己去建立,然后將生成的.class文件放到該目錄下
?? ??? ?執行:java mypack.HelloWorld
?? ??? ??? ?將字節碼文件交給Java虛擬機去解釋執行
?? ??? ??? ?需要注意的事,必須使用包名.類名去解釋執行
?? ??? ??? ?
包(package):把源文件放在目錄下
?? ?由于工程的需要,將不同的源文件放在不同的目錄下,從而引入了包。
?? ?包可以看作就是一個存放java源文件的目錄。
?? ?在源碼中聲明一個包名:package p;(只能放在第一行,且最多只能是一行)
?? ?如果指定多層包,那么在包名之間我們可以用.作為分隔符:package p1.p2.p3.p4;
?? ?用“javac HelloWorld.java –d 絕對路徑”,編譯后生成的字節碼文件就會放在指定的包結構下
?? ?執行該程序需要用" java 包名.類名 "
?? ?引進包中的某個類:import 包名.類名;
?? ?引進包中的所有類:import 包名.*;
?? ??? ??? ?
注釋:
?? ?//?? ?單行注釋, 到本行結束的所有字符會被編譯器忽略
?? ?/* */?? ?多行注釋,? 在/*? */之間的所有字符會被編譯器忽略
?? ?/**? */ ??? ?文檔注釋, java特有的,在/**? */之間的所有字符會被編譯器忽略
?? ?可以用javadoc把java源程序中這種注釋抽取出來形成html頁面(只有寫在包,類,屬性,方法,構造器,引入之前的注釋才可以進行抽取)
?? ? ??? ?
標識符:
?? ?命名規則:
?? ??? ?(1) 由字母、數字、下劃線、$組成,不能以數字開頭
?? ??? ?(2) 大小寫敏感
?? ??? ?(3) 不得使用java中的關鍵字和保留字
?? ?
?? ?關鍵字:都是小寫的,jdk1.2多了strictfp(經準浮點型),關鍵字 jdk1.4多了assert(斷言)關鍵字,? jdk1.5多了enum(枚舉) 關鍵字
?? ??? ?隨著學習進度,會慢慢接觸到的
?? ??? ?true、false、null嚴格說不應該算關鍵字,應稱其為保留字更合適
?? ?
?? ?習慣:
?? ??? ?(1) 標識符要符合語義信息
?? ??? ?(2) 包名所有字母小寫
?? ??? ?(3) 類名每個單詞首字母大寫,其它小寫 //TarenaStudent
?? ??? ?(4) 變量和方法:第一個單詞小寫,從第二個單詞開始首字母大寫 //tarenaStudent
?? ??? ?(5) 常量:所有字母大寫,每個單詞之間用" _ "連接
?? ??? ?
基本數據類型:8種
?? ?1) 整型 ?
?? ??? ?byte?????? 1B?? ? 8位?????? -128到127 ?
?? ??? ?short????? 2B?? ? 16位????? -2^15到(2^15)-1 ?
?? ??? ?int????????? 4B?? ? 32位????? -2^31到(2^31)-1 ?
?? ??? ?long??????? 8B?? ? 64位????? -2^63到(2^63)-1 ?
?? ?2) 浮點類型 ?
?? ??? ?float??????? 4B?? ?? 32位?????? ?
?? ??? ?double???? 8B?? ?? 64位 ?
?? ?3) 字符類型 ?
?? ? ??? ?char?????? 2B?? ?16位 ?? ?
?? ?4) 布爾型 ?? ?1B
?? ??? ?boolean??? false/true
?? ??? ?
?? ?注:
?? ??? ?1、Java中的自動類型提升問題。
?? ??? ??? ?1)、正向過程:從低字節到高字節可以自動轉換。
?? ??? ??? ??? ?byte->short->int->long->float->double
?? ??? ??? ?2)、逆向過程:從高字節到低字節用強制類型轉換。
?? ??? ??? ??? ?例:int a = (int)4.562;
?? ??? ??? ??? ?注:逆向轉換將丟失精度。
?? ??? ? 2、boolean:只有true和false。
?? ??? ? 3、char:Java中用" \u四位十六進制的數字 (即使在注釋中出現\u,后面如果跟的不是4個數字,也會報錯)"表示將字符轉換成對應的unicode編碼,字符類型要用單引號括起來。
?? ??? ? 4、黙認浮點類型為double,float數據類型有一個后綴為" f "或" F "。
?? ??? ? 5、long類型有一個后綴,為" l " 或者" L "
?? ?
引用數據類型:
?? ?類、接口、數組
?? ?引用類型 變量名 = new 引用類型名(參數);?? ??? ?//new后面一般跟的都是類的構造器
?? ?成員:寫在類體括號里面的
?? ?
內存空間的分配:
?? ?內存分為:
?? ??? ?棧:存放簡單數據類型變量(值和變量名都存在棧中),存放引用數據類型的變量名以及它所指向的實例的首地址
?? ??? ?堆:存放引用數據類型的實例
局部變量:不是聲明在類體括號里面的變量
??? (1)必須要先賦值,后使用,否則通不過編譯,局部變量沒有默認初始化值
??? (2)作用范圍:定義開始到定義它的代碼塊結束
??? (3)同一范圍內,不允許2個局部變量命名沖突
?
??? 參數傳遞時,簡單類型進行值轉遞??? (參數進行傳遞時都會先去棧中生成一個副本的,使用結束后釋放)
??? ?
自動類型提升:
??? byte a = 1;
??? byte b = 2;
??? a = a+b;????????? //編譯出錯自動類型提升成int
??? a += b;?????? //自加沒有自動類型提升問題
??? 類型自動提升規則:
??? ??? a和b作某種運算
??? ??? a和b中有double,結果就是double
??? ??? a和b中有float,結果就是float
??? ??? a和b中有long,結果就是long
??? ??? 除此之外,結果都是int
??? 把高字節轉成低字節,需要作強制類型轉換. byte c=(byte)a+b;
??? ?
移位運算符:效率最高
??? >>?? 有符號右移,補符號位
??? ??? 移負數位,則將該數值加32后再進行移位
??? ??? 數值的2進制是按照補碼保存的
??? >>>? 右移后高位都補0
??? ?
邏輯運算符:
??? &/|也可以作為邏輯運算符
??? &&??? 先判斷前面一個條件,如果為假,則不用計算后一個條件
??? ||??? 先判斷前面一個條件,如果為真,則不用計算后一個條件
??? ?
" + "運算符:
??? 兩個操作的對象是數值時,是加法
??? 如果有一個是字符串時,則是字符串的連接
??? ?
流程控制語句:
??? 同Core C++
??? switch中的變量類型只能是byte、 short、int、char四種類型
??? ?
數組:
??? 聲明數組:???
??? ??? 數組能以下列形式聲明:
??? ??? ??? 類型[] array;
??? ??? ??? 類型 array[];??
??? ??? 注:
??? ??? ??? JAVA中推薦用:類型[] array;
??? ??? ??? 一個數組是一個對象
??? ??? ??? 聲明一個數組沒有創建一個對象
??? ??? ??? 聲明時不用指定長度
??? ??? ??? ?
??? 創建數組:
??? ??? 創建基本數據類型數組:int[] i = new int[2];?
??? ??? 創建引用數據類型數組:Student[] s = new Student[100];?
??? ??? 數組創建后其中的元素有初始值
??? ??? ??? 類型???????????????????? 黙認值?
??? ??? ??? byte???????????????????? ??? 0?
??? ??? ??? short??????????????????? ??? 0?
??? ??? ??? int????????????????????? ??? 0?
??? ??? ??? long???????????????????? ??? 0l?
??? ??? ??? float??????????????????? ??? 0.0f?
??? ??? ??? double?????????????????? 0.0d?
??? ??? ??? char???????????????????? ??? \u0000
??? ??? ??? boolean??????????????? ??? false?
??? ??? ??? reference types??? ??? null
??? ??? 注:
??? ??? ??? 創建時一定要指定長度
??? ??? ??? int[] i2=new int[];?????????? ??? //error
??? ??? ??? ?
??? 初始化數組:?
??? ??? 聲明、創建、初始化分開:?
??? ??? ??? int[] i;?? //定義數組
??? ??? ??? i = new int[2]; ??? //分配空間
??? ??? ??? i[0] = 0;?? ??? //初始化
??? ??? ??? i[1] = 1;?
??? ??? ??? ?
??? ??? 聲明、創建、初始化在同一時間 :
??? ??? ??? int[] i = {0,1};? ??? //顯示初始化? {}中有幾個值,則數組長度為幾
??? ??? ??? Student[] s = {new Student(),new Student()};?
??? ??? ??? ?
??? ??? 注:??? int[] i=new int[]{1,2,3};???? ??? //后面[]中不可以寫數值
??? ??? ??? int[] i1=new int[3]{1,2,3};?? ??? //error
??? ??? ??? ?
??? 二維數組:(其實是一個一維數組,它的每一個元素又是一個一維數組)
??? ??? int[][] i1 = new int[2][3];?
??? ??? int[][] i4 = {{1,1,1},{2,2,2},{3,3,3}};
??? ??? int[][] i3 = new int[][3];??? ??? //不允許高維沒分配空間而先給低維分配空間
??? ??? int[][] i2 = new int[2][];?
??? ??? i2[0] = new int[2];
??? ??? i2[1] = new int[3];?????
??? ??? ?
??? 數組長度:
??? ??? 數組的屬性length
??? ??? 數組長度一旦確定,不可改變?????
??? ??? int[] i = new int[5]; 則i.length= 5
??? ??? ?
??? 數組拷貝:
??? ??? 系統類System提供的
??? ??? static void arraycopy(Object src, int srcPos, Object dest, int destPos, int length)?
??? ??? ??? src: 源數組??? ??? ?
??? ??? ??? srcPos: 從源數組哪個位置開始拷貝(位置指的是元素的下標)
??? ??? ??? dest: 目標數組
??? ??? ??? destPos: 拷貝的元素放到目標數組的起始位置
??? ??? ??? length: 拷貝多少個
??? ??? ??? ?
??? 數組排序:
??? ??? 自己實現一個排序方法來進行排序
??? ??? 或者調用java.util.Arrays.sort(Object o)
類和對象:
??? 類:主觀抽象,是對象的模板,可以實例化對象
??? ??? 習慣上類的定義格式:
??? ??? ??? package xxx;??? ??? ?
??? ??? ??? import xxx;??? ??? ?
??? ??? ??? public class Xxxx{
??? ??? ??? ??? 屬性 ······;
??? ??? ??? ??? ?
??? ??? ??? ??? 構造器 ······;
??? ??? ??? ??? ?
??? ??? ??? ??? 方法 ······;
??? ??? ??? }
?
??? ??? 定義屬性:實例變量
??? ??? ??? 格式:[ 修飾符 ]? 類型 變量名? [ = ? ]
??? ??? ??? 實例變量定義在類中但在任何方法之外。
??? ??? ??? 實例變量有默認值:各種各樣的0。(同數組)
??? ??? ??? 實例變量的作用域至少在本類內部,受訪問控制符的限制。
??? ??? ??? 在重合作用域,實例變量和局部變量允許有命名沖突,“局部優先”。
??? ??? ??? ?
??? ??? 定義方法:
??? ??? ??? 格式: [ 修飾符 ]? 返回類型 方法名( 參數列表 ) [ throws? 異常 ] { ······ }?
??? ??? ??? java中所有參數都是值傳遞。
??? ?? ??? ??? 當沒有值返回時,返回類型必須被定義為void。?
??? ??? ??? 返回類型必須與方法名相鄰,其他修飾符可以調換位置。
??? ??? ??? ?
??? ??? 構造器:
??? ??? ??? 在創建對象的過程中調用的方法。
??? ??? ??? 構造器沒有返回類型。
??? ??? ??? 構造器的名字與類名相同。
??? ??? ??? 格式為:[ 修飾符 ]? 類名( 參數列表 ){? },修飾符可以是private、 protected、 default、private
??? ??? ??? 在一個對象的生成周期中構造器只用一次,由系統自動調用,不允許手工調用。
??? ??? ??? 程序員沒有提供一個構造器,系統會自動提供一個無參的構造器。
??? ??? ??? 獲得對象的方式:
??? ??? ??? ??? 通過new(在堆空間中申請分配空間),new 類名(),可以通過這種形式或的一個對象,這時的對象是無法使用,必須把他的地址存放進一個對象變量才能夠使用。
??? ??? ??? ??? 例如 :
??? ??? ??? ??? ??? Car c=new Car();
??? ??? ??? 注意:
??? ??? ??? ??? 最好在寫類時提供一個無參的構造器。
??? ??? ??? ??? ??? ??? ?
??? ??? this關鍵字:
??? ??? ??? this是個隱式參數,代表當前對象;
??? ??? ??? ??? publie class Student{
??? ??? ??? ??? ??? private String name;
??? ??? ??? ??? ??? public void setName(String name){
??? ??? ??? ??? ??? ??? this.name=name;??? ??? //this.name為當前對象的成員變量
??? ??? ??? ??? ??? }
??? ??? ??? ??? }
??? ??? ??? ??? ?
??? ??? ??? 如果某個構造方法的第一個語句具有形式this( ··· ),那么這個構造方法將調用同一類中的其他構造方法。
??? ??? ??? ?
??????? ??? ??? 注意:
??????? ??? ??? ??? 在構造器中this(...)必須放在該構造器的第一行。
??? ??? ??? ??? this不能出現在靜態方法里面??? ??? ?
??? ?
??? 類、對象、實例三者的關系:
??? ??? 類:是對象的模板,可以實例化對象
??? ??? 對象:類的個體
??? ??? 實例:實現的對象
??? ??? student s;??? ?
??? ??? s=new student();
??? ??? ??? 其中 Student為類,s為對象,new Student()為實例,s賦值后也是實例了。
?
方法重載:
??? 方法名相同,參數表不同,不考慮返回值類型(但最好還是使返回類型一致)。
??? 編譯器根據參數,選擇一個方法,如果沒有完全匹配的,對于參數表采用“向上就近匹配原則”,但不允許模棱兩可。
??? 方法重載屏蔽了一個對象的同一類方法由于參數不同所造成的差異。
??? ??? ??? ?
封裝:
??? 類的屬性加private修飾符,來限制只能夠在類的內部進行訪問,有效的保護數據。
??? 對于類中的私有屬性,要對其給出一對方法getXxx(),setXxx()訪問私有屬性,保證對私有屬性的操作的安全性。
??? 方法公開的是方法的聲明,即只須知道參數和返回值就可以調用該方法,隱藏方法的實現的細節。
??? 一個對象和外界的聯系應當通過一個統一的接口,應當公開的公開,應當隱藏的隱藏。
??? ??? ?
繼承:
??? 父類到子類是從一般到特殊的關系。
??? ??? 泛化:將不同子類中的共性抽象成父類的過程。
??? ??? 特化:在原有父類的基礎上加入一些個性的過程。
??? ??? 原則:父類放共性,子類放個性。
??? 繼承的關鍵字:extends
??? Java只支持單繼承:一個類最多只有一個直接的父類。
?
???? ??? 方法覆蓋:
??? ??? 方法名:相同
??? ??? 參數表:相同
??? ??? 訪問限制符:相同或者更寬
??? ??? 返回值類型:相同或者子類返回的類型是父類返回的類型的子類(在JDK5.0以后)
??? ??? 拋出的異常:不能比父類更寬。
?????
???? ??? super關鍵字:
??? ??? super()表示調用父類的構造器
??? ??? super()也和this()一樣必須放在方法的第一句
??? ??? super()和this()不能同時出現?????????
??? ??? super可以屏蔽子類屬性和父類屬性重名時帶來的屬性遮蓋,super. 表示調用父類的方法或屬性
??? ??? 在子類的構造器中如果沒有指定調用父類的哪一個構造器,那么就會調用父類的無參構造器,即super()
??? ??? ?
??? 注意:
??? ??? 父類的構造器不能被子類繼承
??? ??? 方法和屬性可以被繼承,權限不限制能否繼承過來,限制的是能否直接訪問
??? ??? 先構造父類,后構造子類,先this后super
??? ??? ?
多態:
??? 多態分為兩種:編譯時多態和運行時多態。
??? ??? 編譯時類型:主觀概念,把它看作什么。
??? ??? 運行時類型:客觀概念,實際它是什么。
??? ? ??? 例:Animal a=new Dog();
??? ????? ??? ??? 指著狗問,這個動物是什么?
??? ????? ??? ??? ?
???? ??? 運行時多態的三原則:
??? ??? 對象類型不變。
??? ??? 只能對對象調用編譯時類型中定義的方法。
??? ??? 在程序的運行時,根據對象的運行時類型,找覆蓋后的方法來調用。(運行時動態類型綁定)
??? ??? ?
???? ??? 強制類型轉換: 一定沒有新對象生成。(父類的引用賦值給子類的引用需要進行強制類型轉換)
???? ??? 關鍵字:instanceof
????????? ??? 用法:引用? instanceof? 類名??? 判斷這個引用所指向的對象是否屬于這個類。
??? ? ??? 用在強制轉換之前,避免類型轉換異常。
??? ??? ??? if(a instanceof Dog){
??? ??? ??? ??? Dog d=(Dog)a;
??? ??? ??? }
??? ??? ??? ?
??? 多態的作用:把不同的子類對象都當作父類來看,可以屏蔽不同子類對象之間的差異,寫出通用的代碼,做出通用的編程,以適應需求的不斷變化。
修飾符static: 把對象相關的變成類相關的,它可以修飾屬性、方法、代碼塊和內部類
??? static修飾屬性(類變量):
??? ??? 那么這個屬性就可以用" 類名.屬性名 "來訪問,也就是使這個屬性成為本類的類變量,為本類對象所共享。
??? ??? 類加載的過程,類本身也是保存在文件中(字節碼文件保存著類的信息)的,java會通過I/O流把類的文件讀入JVM(java虛擬機),這個過程稱為類的加載。JVM會通過類路徑(CLASSPATH)來找字節碼文件。需要的時候才會進行類加載,生成對象時是先加載后構造
??? ??? 類變量,會在加載時自動初始化,初始化規則和實例變量相同。
??? ??? 注意:
??? ??? ??? 類中的實例變量是在創建對象時被初始化的
??? ??? ??? static修飾的屬性,是在類加載時被創建并進行初始化,類加載的過程只進行一次,也就是類變量只會被創建一次。
??? ??? ??? ?
??? static修飾方法(靜態方法):
??? ??? 會使這個方法成為整個類所公有的方法,可以用" 類名.方法名 "訪問。
??? ??? static修飾的方法,不能直接訪問本類中的非靜態成員,但本類的非靜態方法可以訪問本類的靜態成員。
??? ??? 在靜態方法中不能出現this關鍵字。
??? ??? 父類中是靜態方法,子類中不能覆蓋為非靜態方法,在符合覆蓋規則的前提下,在父子類中,父類中的靜態方法可以被子類中的靜態方法覆蓋,但是沒有多態。(在使用對象調用靜態方法時其實是調用編譯時類型的靜態方法)
??? ??? java中的main方法必須寫成static的原因:在類加載時無法創建對象,而靜態方法可以不通過對象調用,所以在類加載時就可以通過main方法入口來運行程序。
??? ??? ?
??? static修飾初始代碼塊:
??? ??? 這時這個初始代碼塊就叫做靜態初始代碼塊,這個代碼塊只在類加載時被執行一次。
??? ??? 可以用靜態初始代碼塊初始化一個類。
??? ??? 動態初始代碼塊,寫在類體中的“{}”,這個代碼塊是在生成對象時運行,這種代碼塊叫動態初始代碼塊。
??? ??? ?
單例設計模式:
??? 一個類只允許有一個對象,保證所有引用的對象都是同一個對象。
??? 因為只允許存在一個對象,則不允許在外面直接new出新的對象,所以應該把構造器設為private,。
??? 在類內定義一個公開的靜態方法,讓使用者進行調用,通過該方法去獲得一個實例。
??? 例:
??? ??? public calss Singleton{
??? ??? ??? private static Singleton s;
??? ??? ??? private Singleton(){}
??? ??? ??? public static Singleton newInstance(){
??? ??? ??? ??? if ( s == null)
??? ??? ??? ??? ??? s = new Singleton();
??? ??? ??? ??? return s;
??? ??? ??? }
??? ??? }??? ?
??? ??? ?
修飾符final:不允許改變,可以修飾變量、方法、類
??? final修飾變量:
??? ??? 被fianl修飾的變量就會變成常量,一旦賦值不能改變
??? ??? 常量可以在初始化時直接賦值,也可以在構造方法里賦值,只能在這兩種方法里二選一,不能不為常量賦值
??? ??? 常量不會有默認初始值
??? ??? 鎖定棧,使棧中的數據不可以改變
??? ??? 靜態常量只能在初始化時直接賦值
??? ??? ?
??? final修飾方法:
??? ??? 被final修飾的方法將不能被其子類覆蓋,保持方法的穩定不能被覆蓋
??? ?
??? final修飾類:
??? ??? 被final修飾的類將不能被繼承
??? ??? final類中的方法也都是final的
??? ?
??? 注意:
??? ??? final不能用來修飾構造方法
??? ??? ?
訪問權限控制:??? ?
??? private:
??? ??? 本類內部可以訪問
??? ??? 不能繼承到子類
??? default:
??? ??? 本類內部可以訪問,同包其他類也可以訪問。
??? ??? 同包可繼承
??? protected:
??? ??? 本類內部可以訪問,不同包的子類也可以訪問,同包其他類也可以訪問。
??? ??? 能繼承到子類
??? public:
??? ??? 任何地方都可以訪問??
??? ??? 能繼承到子類
修飾符abstract:抽象的,定義框架不去實現,可以修飾類和方法
??? abstract修飾類:
??? ??? 會使這個類成為一個抽象類,這個類將不能生成對象實例,但可以做為對象變量聲明的類型,也就是編譯時類型
??? ??? 抽象類就相當于一個類的半成品,需要子類繼承并覆蓋其中的抽象方法,這時子類才又創建實例的能力,如果子類沒有實現父類的抽象方法,那么子類也要為抽象類。
??? ?
??? abstract修飾方法:
??? ??? 會使這個方法變成抽象方法,也就是只有聲明而沒有實現,實現部分以";"代替,需要子類繼承實現。
??? ??? 抽象方法代表了某種標準,定義標準,定義功能,在子類中去實現功能(子類繼承了父類并需要給出從父類繼承的抽象方法的實現)。
??? ??? 方法一時間想不到怎么被實現,或有意要子類去實現而定義某種標準,這個方法可以被定義為抽象。
??? ?
??? 注意:
??? ??? 有抽象方法的類一定是抽象類。但是抽象類中不一定都是抽象方法,也可以全是具體方法。
?
接口(interface):
??? 接口的定義:接口從本質上說是一種特殊的抽象類。
??? ??? 關鍵字interface。
??? ??? 在接口中,所有的方法為公開、抽象的方法:public abstract
??? ??? 在接口中,所有的屬性都是公開、靜態的常量:public static final
??? ??? 接口與接口之間可以多繼承,用extends,多個之間用逗號隔開。
??? ??? 接口中沒有構造方法,不能用“new 接口名”來實例化一個接口,但可以聲明一個接口。
??? ?
??? 接口的實現:
??? ??? 關鍵字implements
??? ??? 一個類實現一個接口必須實現接口中所有的方法,否則其為抽象類,并且在實現類中的方法要加上public(不能省略)。
??? ??? ??? 類中的默認修飾符:default。
??? ??? ??? 接口中的默認修飾符:public。
??? ??? 一個類除了繼承另一個類外(只能繼承一個類),還可以實現多個接口(接口之間用逗號分隔)。
?
??? 接口的作用:
??? ??? 間接實現多繼承:用接口來實現多繼承并不會增加類關系的復雜度。因為接口不是類,與類不在一個層次上,是在類的基礎上進行再次抽象。
??? ??? 接口可以抽象出次要類型,分出主、次關系類型,符合看世界的一般方法。
??? ??? 接口隔離,與封裝性有關。一個對象都有多個方面,可以只展示其中幾個方面,其他的都隱藏。因此可以看為“更高層次的封裝”,把??? ??? ??? 一個大接口做成若干個小接口。
??? ??? 通過接口制定標準(最重要的作用)
??? ??? ??? 接口:制定標準。
??? ??? ??? 接口的調用者:使用標準。
??? ??? ??? 接口的實現類:實現標準。
??? ??? ??? ??? 解耦合作用:把使用標準和實現標準分開,使得標準的制定者和實現者解除偶合關系,具有極強的可移植性
??? ??? ??? ??? 例:sun公司提供一套訪問數據庫的接口(標準),java程序員訪問數據庫時針對數據庫接口編程。接口由各個數據庫廠商負責實現。
??? ??? ?????
??? 接口編程的原則
??? ??? 盡量針對接口編程(能用接口就盡量用接口)
??? ??? 接口隔離原則(用若干個小接口取代一個大接口)
??? ??? ?
??? 注意:
??? ??? 接口中沒有構造器,也沒有main方法
??? ??? ?
封裝類:
??? Java為每一個簡單數據類型提供了一個封裝類。
??? 除int和char,其余類型首字母大寫即成封裝類。
??? ??? int??????????????? Integer
??? ??? char???????????? Character
??? 最常用的兩個封裝類Integer和Double
??? jdk1.4之前基本類型和封裝類的轉化是需要構造器去轉化的,到了jdk1.5是自動進行轉化的
??? int、Integer和String之間的轉化(最常用的)
??? ??? int i=1;
??? ??? Integer in = new Integer(i);??? ??? ??? ??? //int --> Integer?
??? ??? int? i = in.intValue();??? ??? ??? ??? ??? //Integer --> int?
??? ??? String? str = String.valueOf(i);??? ??? ??? //Int --> String
??? ??? int? ii = Integer.parseInt(str);??? ??? ??? //String --> int
??? ??? String? s = in.toString();??? ??? ??? ??? ??? //Integer --> String
??? ??? Integer inte = Integer.valueOf(str);??? ??? //String --> Integer??????
?
Object類
??? hashCode():
??? ??? 返回該對象的哈希碼值
??? ??? hashCode 的常規協定是:?
??? ??? ??? 在 Java 應用程序執行期間,在同一對象上多次調用 hashCode 方法時,必須一致地返回相同的整數,前提是對象上 equals 比較中所用的信息沒有被修改。
??? ??? ??? 如果根據 equals(Object) 方法,兩個對象是相等的,那么在兩個對象中的每個對象上調用 hashCode 方法都必須生成相同的整數結果。?
??? ??? ??? ?
??? toString():
??? ??? 返回該對象的字符串表示。
??? ??? 通常,toString 方法會返回一個“以文本方式表示”此對象的字符串。結果應是一個簡明但易于讀懂。建議所有子類都重寫此方法。
??? ??? ?
??? equals()
??? ??? 指示某個其他對象是否與此對象“相等”。?
??? ??? equals 方法在非空對象引用上實現相等關系:?
??? ??? ??? 自反性:對于任何非空引用值 x,x.equals(x) 都應返回 true。?
??? ??? ??? 對稱性:對于任何非空引用值 x 和 y,當且僅當 y.equals(x) 返回 true 時,x.equals(y) 才應返回 true。?
??? ??? ??? 傳遞性:對于任何非空引用值 x、y 和 z,如果 x.equals(y) 返回 true,并且 y.equals(z) 返回 true,那么 x.equals(z) 應返回 true。?
??? ??? ??? 一致性:對于任何非空引用值 x 和 y,多次調用 x.equals(y)始終返回 true 或始終返回 false,前提是對象上 equals 比較中所用的信息沒有被修改。對于任何非空引用值 x,x.equals(null) 都應返回 false。?
??? ??? ??? 注意:
??? ??? ??? ??? 當此方法被重寫時,通常有必要重寫 hashCode 方法,以維護 hashCode 方法的常規協定,該協定聲明相等對象必須具有相等的哈希碼。?
?
String、StringBuffer和StringBulder??? ?
??? String: 不可改變的Unicode字符序列
??? ??? 池化思想,把需要共享的數據放在池中,用一個存儲區域來存放一些公用資源以減少存儲空間的開銷。
??? ??? 在String類中,以字面值創建時,會到Java方法空間的串池中去查找,如果沒有則會在串池里創建一個字符串對象,并返回其地址賦給對象變量,如果有就返回串池中字符串的地址,并把這個地址賦給對象變量。
??? ??? 如果是new,則會在堆空間中創建String類的對象,不會有上述的過程
??? ??? 如:
??? ??? ??? String s1 = "abc";??????????? //新創建,字符串常量池中沒有該串,則會在池中創建一個串"abc"
??? ??? ??? String s2 = "abc";??????????? //串池中已經存在"abc",則s2會去指向"abc"而不會去創建一個新的
??? ??? ??? String s3 = new String("abc");?????????? //直接在堆中去開辟一個新的空間,而不會去池中查找
??? ??? 類中的具體方法查看下Api文檔。
??? ??? 調用任何String中的方法,不會改變String自身,除非重新賦值。
??? ??? ??? ?
??? StringBuffer: 可改變的Unicode字符序列
??? ??? 允許并發操作,是線程安全的
??? ??? String類在進行字符串連接時會顯得效率很低,就是因為它所產生的對象的屬性是不能夠修改的,當連接字符串時也就只能創建新的對象。
??? ??? 對于很多字符串連接時,應當使用StringBuffer類,使用這個類的對象來進行字符串連接時就不會有多余的中間對象生成,從而優化了效率。
??? ??? 例:對于字符串連接String str = "A" + "B" + "C" + "D";
??? ??? ??? 產生:"AB"、"ABC"、"ABCD"
??? ??? ??? 在串池中產生的"AB"、"ABC"明顯是多余對象,浪費空間。
??????????????????? ??? 解決方案:
??? ??? ??? ??? String s = null;
??? ??? ??? ??? StringBuffer sb = new StringBuffer("A");
??? ??? ??? ??? sb.append("B");
??? ??? ??? ??? sb.append("C");
??? ??? ??? ??? sb.append("D");
??? ??? ??? ??? s = sb.toString();
??? ??? ??? ??? ??? ?
??? StringBulder: 可改變的Unicode字符序列
??? ??? 操作同StringBuffer,只是不支持并發操作,非線程安全的
集合:保存多個其他對象的對象,不能保存簡單類型
??? List:有序(存放元素的順序),可重復的集合
??? ??? ArrayList:實質就是一個會自動增長的數組
??? ??? ??? 查詢效率比較高,增刪的效率比較低,適用于查詢比較頻繁,增刪動作較少的元素管理的集合。
??? ??? ??? 加載大批量的數據時,先進行手動擴容(就是調用ensureCapacity(int minCapacity)方法),這樣可以提高效率。
??? ??? ??? ?
??? ??? LinkedList:底層是用雙向循環鏈表來實現的
??? ??? ??? 查詢效率低,但是增刪效率很高,適用于增刪動作的比較頻繁,查詢次數較少的元素管理的集合
?
??? Set:無序的,不允許有重復元素的集合
??? ??? HashSet:
??? ??? ??? Object類中的hashCode()的方法是所有類都會繼承的方法,這個方法會算出一個Hash碼值返回,HashSet會用Hash碼值去和數組長度取模,對象的模值(這個模值就是對象要存放在數組中的位置,和數組的下標相同)相同時才會判斷數組中的元素和要加入的對象的內容是否相同,如果不同才會再找位置添加進去,相同則不允許添加。
??? ??? ??? 如果數組中的元素和要加入的對象的hashCode()返回了相同的Hash碼值,才會用equals()方法來判斷兩個對象的內容是否相同。??? ?
??? ??? ??? 注意:要存入HashSet的集合對象中的自定義類必須覆蓋hashCode()、equals()兩個方法,才能保證集合中元素不重復。
??? ??? ??? ?
??? ??? TreeSet:可排序的Set
??? ??? ??? SortedSet接口是Set的子接口,TreeSet是SortedSet接口的實現類,他可以對集合中的元素進行排序。
??? ??? ??? ?
??? ??? ??? 將自定義類的對象存放在TreeSet中,這個類需要實現了Comparable接口,TreeSet可以自動過濾掉重復元素所以不在需要重載hashCode()方法,TreeSet會根據比較規則判斷元素內容是否相同,不同則會存入,TreeSet會在元素存入時就進行排序。
??? ??? ??? ?
??? ??? ??? Comparable接口:
??? ??? ??? ??? 也叫做可比較接口,這個接口在java.lang包下,只要根據指定類型的排序規則實現了這個接口,就是可排序的。
??? ??? ??? ??? 這個接口中只定義了一個 compareTo(Object o) 方法,該方法的返回值類型是整型,如果當前對象大于參數對象就返回正數,當前對象等于參數對象就返回0,當前對象小于參數對象就返回負值,這樣寫就是升序排列,反之則是進行降序排列。
??? ??? ??? ??? ?
??? ??? ??? Comparator接口:
??? ??? ??? ??? 比較器Comparator接口,是另一種對自定義類型對象的集合整體排序的方法,存在于java.util包下。
??? ??? ??? ??? 這個接口中定義了一個 compare(Object o1,Object o2) 方法來比較兩個對象,這個方法的返回值定義和上面介紹的那個方法是一樣。
??? ??? ??? ??? 利用這種方式,則在創建集合的時候把定義好的比較器作為參數,構造一個集合
??? ??? ??? ??? ?
??? Map:存放key-value對(有關系的兩個對象,一個做key,一個做value,同時存入)
??? ??? HashMap:基于哈希表的 Map 接口的實現,此實現提供所有可選的映射操作,并允許使用 null 值和 null 鍵
??? ??? ??? 遍歷:
??? ??? ??? ??? 先調用keySet()得到key的set集合,
??? ??? ??? ??? 再迭代遍歷key的set集合,
??? ??? ??? ??? 根據key得到value。
??? ??? ??? ??? ?
??? ??? Hashtable:同HashMap,一般不使用
??? ??? ?
??? ??? HashMap與Hashtable的區別:
??? ??? ??? HashMap:非線程安全,不支持并發控制,允許空的鍵值對。
??? ??? ??? Hashtable:是線程安全,支持并發控制,不允許有空的鍵值對。
??? ??? ??? ?
??? ??? SortedMap接口:Map的子接口,按某一特定排序規則來存放所加入的鍵值對
??? ??? ??? 實現類:TreeMap類。
??? ??? ??? ??? Key值的排序規則,同SortedSet接口實現類TreeSet
??? ??? ??? ??? ?
??? ??? 注意:
??? ??? ??? key一般是8種基本類型的封裝類或者是String類,拿自己自定義的類作為Key沒有意義。
??? ??? ??? key不可重復,value可以重復
??? ??? ????
反射:
??? 反射:在運行時動態分析或使用一個類進行工作。
??? java.lang.Class類:描述類信息的類。
??? 類對象:描述一個類信息的對象,當虛擬機加載類的時候,就會創建這個類的類對象并加載該對象,Class是類對象的類型。
??? ?
??? 獲得類對象的方式:
??? ??? 用" 類名.class "獲得這個類的類對象。
??? ??? 用類的對象掉用getClass(),如object.getClass()得到這個對象的類型的類對象。
??? ??? 可以使用Class.forName(類名),也可以得到這個類的類對象,(注意,這里寫的類名必須是全限定名(全名),是包名加類名,XXX.XXX.XXXX)。
??? ??? 基本類型也有類對象,用" 封裝類.TYPE "可以獲得對應的基本類型的類對象。
?
??? java.lang.reflect包下的三個重要類:
??? ??? Field屬性類:用來描述屬性的信息。
??? ??? Method方法類:方法的信息的描述。
??? ??? Constructor構造方法類:用來描述構造方法的信息。
?
??? Class類中的常用方法:
??? ??? newInstance()?
??? ??? ??? 創建此 Class 對象所表示的類的一個新實例(調用無參構造創建的對象)。
??? ??? getDeclaredMethods()
??? ??? ??? 獲得的是一個Method方法類對象的數組,獲得本類(不包括父類)聲明的所有(包括private的)方法對象。
??? ??? getMethods()???? //推薦使用
??? ??? ??? 獲得的是一個Method方法類對象的數組,獲得所有(父類的也包括)publice的方法對象。
??? ??? getDeclaredConstructors()
??? ??? ??? 獲得的是一個Constructor構造方法類對象的數組,獲得這個類聲明的所有構造方法對象。
??? ??? getConstructors()??? //推薦使用
??? ??? ??? 獲得的是一個Constructor構造方法類對象的數組,獲得所有publice的構造方法對象。
??? ??? getDeclaredFields()??? //推薦使用
??? ??? ??? 獲得的是一個Field屬性類對象的數組,獲得本類聲明的所有屬性的屬性對象。
??? ??? getFields()
??? ??? ??? 獲得的是一個Field屬性類對象的數組,獲得所有publice的屬性對象。
??? ??? ??? ?
??? 使用反射構造一個類的對象的步驟:
??? ??? a. 獲得類對象
??? ??? b. 獲得構造方法對象
??? ??? c. 獲得對象,用構造方法對象調用構造方法,如果使用無參構造方法,可以跳過第二步,直接使用" 類對象.newInstance() "方法來獲得這個類的對象
??? ??? d. 獲得方法對象
??? ??? e. 用方法對象調用方法(用這個類的對象作為第一參數)
??? ??? 如下面的例子:
??? ??? ??? 反射機制的實現類:
??? ??? ??? ??? package day07.reflect;??? ??? ??? ??? ?
??? ??? ??? ??? import java.lang.reflect.Field;
??? ??? ??? ??? import java.lang.reflect.Method;
??? ??? ??? ??? import java.util.HashMap;
??? ??? ??? ??? import java.util.Map;
??? ??? ??? ??? import java.util.Set;??? ??? ??? ?
??? ??? ??? ??? public class TestReflect {??? ??? ??? ??? ??? ?
??? ??? ??? ??? ??? public static Object get(String className , Map<String,Object> map) throws Exception{
??? ??? ??? ??? ??? ??? Class c = Class.forName(className);????????????????? //獲得類對象
??? ??? ??? ??? ??? ??? Object o = c.newInstance();?????????????????? //獲得對象
??? ??? ??? ??? ??? ??? Set<String> set = map.keySet();
??? ??? ??? ??? ??? ??? for(String str : set){
??? ??? ??? ??? ??? ??? ??? String s = "set" + str.substring(0,1).toUpperCase()+str.substring(1);
??? ??? ??? ??? ??? ??? ??? Field f = c.getDeclaredField(str);
??? ??? ??? ??? ??? ??? ??? Method m = c.getMethod(s, f.getType());??????? //獲得方法對象
??? ??? ??? ??? ??? ??? ??? m.invoke(o, map.get(str));?????????????????????? //用方法對象調用方法
??? ??? ??? ??? ??? ??? }
??? ??? ??? ??? ??? ??? return o;
??? ??? ??? ??? ??? }
??? ??? ??? ??? ??? ?
??? ??? ??? ??? ??? public static void main(String[] args) throws Exception {??? ?
??? ??? ??? ??? ??? ??? Map m = new HashMap();
??? ??? ??? ??? ??? ??? m.put("name", "zhang");
??? ??? ??? ??? ??? ??? m.put("age", 22);
??? ??? ??? ??? ??? ??? Object o = get("day07.reflect.Student",m);
??? ??? ??? ??? ??? ??? Student s = (Student) o;
??? ??? ??? ??? ??? ??? System.out.println(s.getName() + "?? " + s.getAge());
??? ??? ??? ??? ??? ??? ?
??? ??? ??? ??? ??? ??? Map m1 = new HashMap();
??? ??? ??? ??? ??? ??? m1.put("name", "li");
??? ??? ??? ??? ??? ??? m1.put("gender", "男");
??? ??? ??? ??? ??? ??? Object o1 = get("day07.reflect.Teacher",m1);
??? ??? ??? ??? ??? ??? Teacher t = (Teacher) o1;
??? ??? ??? ??? ??? ??? System.out.println(t.getName() + "??? " + t.getGender());
??? ??? ??? ??? ??? }
??? ??? ??? ??? }
??? ??? ??? 學生類:
??? ??? ??? ??? package day07.reflect;??? ??? ??? ??? ?
??? ??? ??? ??? public class Student {
??? ??? ??? ??? ??? private String name;??? ??? ??? ??? ?
??? ??? ??? ??? ??? private int age;??? ??? ??? ??? ?
??? ??? ??? ??? ??? public int getAge() {
??? ??? ??? ??? ??? ??? return age;
??? ??? ??? ??? ??? }??? ??? ??? ??? ?
??? ??? ??? ??? ??? public void setAge(int age) {
??? ??? ??? ??? ??? ??? this.age = age;
??? ??? ??? ??? ??? }??? ??? ??? ??? ?
??? ??? ??? ??? ??? public String getName() {
??? ??? ??? ??? ??? ??? return name;
??? ??? ??? ??? ??? }??? ??? ??? ??? ?
??? ??? ??? ??? ??? public void setName(String name) {
??? ??? ??? ??? ??? ??? this.name = name;
??? ??? ??? ??? ??? }
??? ??? ??? ??? }??? ?
??? ??? ??? 教師類:
??? ??? ??? ??? package day07.reflect;??? ??? ??? ??? ?
??? ??? ??? ??? public class Teacher {
??? ??? ??? ??? ??? private String name;??? ??? ??? ??? ?
??? ??? ??? ??? ??? private String gender;??? ??? ??? ??? ?
??? ??? ??? ??? ??? public String getGender() {
??? ??? ??? ??? ??? ??? return gender;
??? ??? ??? ??? ??? }??? ??? ??? ??? ?
??? ??? ??? ??? ??? public void setGender(String gender) {
??? ??? ??? ??? ??? ??? this.gender = gender;
??? ??? ??? ??? ??? }??? ??? ??? ??? ??? ??? ?
??? ??? ??? ??? ??? public String getName() {
??? ??? ??? ??? ??? ??? return name;
??? ??? ??? ??? ??? }??? ??? ??? ??? ?
??? ??? ??? ??? ??? public void setName(String name) {
??? ??? ??? ??? ??? ??? this.name = name;
??? ??? ??? ??? ??? }??? ??? ??? ??? ?
??? ??? ??? ??? }
??? ?
內部類:
??? 定義:
??? ??? 定義在另外一個類中的類,就是內部類。
??? ??? 編譯后生成的兩個獨立的類:Outer.class 和Outer$Inner.class。
??? ??? ?
??? 內部類的分類:
??? ??? 靜態內部類:靜態內部類定義在類中,任何方法外,用static修飾
??? ??? ??? 靜態內部類只能訪問外部類的靜態成員。
??? ??? ??? 在外部類的外部,要創建一個靜態內部類對象不需要外部類對象:
??? ??? ??? ??? Outer.Inner in = new Outer.Inner();
??? ??? ??? 在本類內部生成內部類對象的方式:
??? ??? ??? ??? Inner in = new Inner();??? ?
??? ?
??? ??? 成員內部類:作為外部類的一個成員存在,與外部類的屬性、方法并列
??? ??? ??? 在內部類中可以直接訪問外部類的私有屬性。
??? ??? ??? 內部類和外部類的實例變量允許命名沖突。
??? ??? ??? ??? 在內部類中訪問實例變量:this.屬性
??? ??? ??? ??? 在內部類訪問外部類的實例變量:外部類名.this.屬性
??? ??? ??? 在外部類的外部,要創建一個成員內部類對象,要首先建立一個外部類對象,然后再創建一個成員內部類對象。
??? ??? ??? ??? Outer out = new Outer();
??? ??? ??? ??? Outer.Inner in = out.new Inner();
??? ??? ??? 在本類內部生成內部類對象的方式:
??? ??? ??? ??? 在靜態方法中:Inner in = new Outer().new Inner();
??? ??? ??? ??? 在非靜態方法中:Inner in = this.new Inner();
??? ??? ??? 成員內部類不可以有靜態成員,這是因為靜態屬性是在加載類的時候創建,這個時候內部類還沒有被創建。
??? ??? ??? ??? ?
??? ??? 局部內部類:在外部類的方法中定義的內部類
??? ??? ??? 與局部變量類似,在局部內部類前不可以加修飾符public和private,其作用域為定義它的代碼塊。
??? ??? ??? 局部內部類不僅可以訪問外部類的實例變量,還可以訪問外部類的局部變量,但要求外部類的局部變量必須為final的。
??? ??? ??? 配合接口使用,來做到強制弱耦合。
??? ??? ??? 在外部類的外部不可創建局部內部類對象,只能在局部內部類所在的方法中創建:
??? ??? ??? ??? Inner in = new Inner();
??? ??? ??? ?
??? ??? 匿名內部類:一種特殊的局部內部類
??? ??? ??? 沒有名字,也沒有class、extends、implements關鍵字
??? ??? ??? 用一種隱含的方式實現一個接口或繼承一個類,并且只能創建一次實例。
??? ??? ??? 實現方式:在某個語句中,new 父類/父接口名字(){ 類體中實現方法 }
??? ??? ??? ??? 例如:
??? ??? ??? ??? ??? TreesSet ts = new TreeSet(new Comparator(){
??? ??? ??? ??? ??? ??? public int compare(Object o1, Object o2){
??? ??? ??? ??? ??? ??? ??? return 0;
??? ??? ??? ??? ??? ??? }
??? ??? ??? ??? ??? });
??? ??? ??? 匿名內部類屬于局部內部類,那么局部內部類的所有限制都對其生效。
??? ??? ??? 匿名內部類是唯一一種無構造方法的類,因為構造器的名字必須合類名相同,而匿名內部類沒有類名。
異常:
??? 異常的分類
??? ??? Java會將所有的異常封裝成對象,其根本父類為Throwable。
??? ??? Throwable有兩個子類:Error 和Exception。
??? ??? ?
??? ??? Error:一個Error對象表示一個程序錯誤,指的是底層的低級的不可恢復的嚴重錯誤
??? ??? ??? 遇到Error,程序一定會退出,因為已經失去了運行所必須的物理環境。
??? ??? ??? 對于Error我們無法進行處理,因為我們是通過程序來應對錯誤的,可是程序已經退出了。
??? ??? ??? ?
??? ??? Exception:由特定因素,導致程序無法繼續,但不影響虛擬機的正常執行。
??? ??? ??? 未檢查異常(Runtime Exception):
??? ??? ??? ??? 是因為程序員沒有進行必要的檢查,由于程序員的疏忽而引起的異常。
??? ??? ??? ??? 對于未檢查異常可以不處理,編譯可以通過,應對未檢查異常的方法就是養成良好的檢查習慣
??? ??? ??? 已檢查異常(非Runtime Exception):
??? ??? ??? ??? 是不可避免的,對于已檢查異常必須處理,否則編譯不通過。
?
??? 異常處理的機制:
??? ??? 當一個方法中有一條語句出現了異常,它就會throw(拋出)一個異常對象(throw 異常對象),然后后面的語句不會執行,而返回上一級方法,其上一級方法接受到了異常對象之后,有可能對這個異常進行處理(進行處理則不會上拋),也可能將這個異常傳到它的上一級,如果最上一級(main方法)不處理就會傳給虛擬機,虛擬機就會終止程序的運行。
?
??? 異常的處理方式:throws和try-catch方法
??? ??? try-catch處理方式:
??? ??? ??? ??? try{??? ??? //一個
??? ??? ??? ??? ?
??? ??? ??? ??? ??? (1)可能出現異常的語句
??? ??? ??? ??? ??? ?
??? ??? ??? ??? } catch(XxxException e /*捕獲的異常*/){??? //0或n個
??? ??? ??? ??? ?
??? ??? ??? ??? ??? (2)處理異常的代碼
??? ??? ??? ??? ??? ?
??? ??? ??? ??? } finally{??? ??? //0或1個
??? ??? ??? ??? ?
??? ??? ??? ??? ??? (3)必須要執行的代碼
??? ??? ??? ??? ??? ?
??? ??? ??? ??? }
??? ??? ??? ??? (4)方法中的其他代碼
??? ??? ??? ??? ??? ?
??? ??? ??? 如果代碼正確,那么程序不經過catch語句直接向下運行;
??? ??? ??? 如果代碼不正確,則將返回的異常對象和e進行匹配,如果匹配成功,則處理其后面的異常處理代碼。
??? ??? ??? try中如果發現錯誤,即跳出try塊去匹配catch,那么try后面的語句就不會被執行。
??? ??? ??? 一個try可以跟多個catch語句,用于處理不同情況,但是不能將父類型的exception的位置寫在子類型的excepiton之前。
??? ??? ??? 在try-catch后還可以再跟一子句finally。其中的代碼語句論有沒有異常都會被執行(因為finally子句的這個特性,所以一般將釋放資源,關閉連接的語句寫在里面)。
??? ??? ??? finally中的代碼和try-catch中的代碼沖突時,finally中的代碼一定會被執行且會忽略try-catch中的代碼。但是如果try-catch中有System.exit(0);(虛擬機退出語句),則不會去執行fianlly中的代碼。
??? ??? ?
??? ??? throws/throw處理方式:
??? ??? ??? throw 寫在方法內,后面跟一個異常對象。
??? ??? ??? throws 在方法的定義中說明方法可能拋出的異常,后面跟異常類的名字,聲明這個方法將不處理異常,把異常交給上一級方法處理。
??? ??? ??? 調用時,調用者不能拋出范圍更小的異常。
??? ??? ??? 對于方法a,如果它定義了throws Exception。那么當它調用的方法b返回異常對象時,方法a并不處理,而將這個異常對象向上一級返回,如果所有的方法均不進行處理,返回到主方法,如主方法也不進行處理,則到虛擬機中,程序中止。
??? ??? ??? 如果在方法的程序中有一行throw new Exception(),那么其后的程序不執行,如果沒有對這個可能出現的檢查結果進行處理,那么程序就會報錯。
??? ??? ??? throws和throw沒有必然的聯系。
??? ?
??? ??? 注意:
??? ??? ??? 方法的覆蓋中,如果子類的方法拋出的例外是父類方法拋出的例外的父類型,那么編譯就會出錯:子類無法覆蓋父類。
??? ??? ??? 子類拋出的例外或者與父類拋出的例外一致,或者是父類拋出例外的子類型,或者子類型不拋出例外。
??? ??? ??? 如果父類型無throws時,子類型也不允許出現throws。此時只能使用try catch。
?
??? ??? 自定義異常:
??? ??? ??? a. 使其繼承Exception或者RuntimeException。
??? ??? ??? b. 寫構造器,直接調用父類的構造器
??? ??? ??? ?
斷言(assert):用來調試、測試代碼
??? 格式:
??? ??? assert 布爾表達式: 字符串? (如果布爾表達式為false時,這個字符串才會顯示)
??? 注意:
??? ??? assert默認是關閉的,使用時需要使用" -ea "進行開啟," -da "是關閉,如:java -ea 類名。
??? ??? 斷言是以異常方式去執行的,當斷言的布爾表達式為假時,會中斷代碼。
??? ??? 不能繼承性的打開(java -ea:類名? 這樣只能打開該類,如果存在父類,不會去打開父類)
??? ??? ?
圖形界面:
??? AWT:抽象窗口工具(Abstract Window Toolkit)
??? ??? 組件:圖形界面中所有能看到的,比如按鈕等。
??? ??? 容器:用來管理其他組件的對象
??? ??? 布局管理器:布置組件在容器中的位置和大小
??? ??? ?
??? Swing:AWT的一個增強版
??? ??? ?
??? 構造圖形界面的步驟:
??? ??? 選擇一個容器
??? ??? 設置容器的布局管理器
??? ??? 向容器中添加組件
??? ??? 事件的監聽
??? ??? ?
??? 容器(Container):用于管理其他的組件的對象,組件必須放到容器里
??? ??? JFrame:一個最頂層的窗體容器,所有其他的組件必須放在頂層容器里。
??? ??? JPanel:不是頂層容器,必須放在頂層容器中,是透明的(默認)。
??? ??? 容器的方法:
??? ??? ??? add(Component com)? 將組件加入容器。?
??? ??? ??? setLayout(LayoutManager manager)? 設置布局管理器。?????
??? ??? ??? setSize(int width,int height)? 設置窗口大小
??? ??? ??? setVisible(boolean b)? 顯示或隱藏此組件
??? ??? ??? setDefaultCloseOperation(int operation)? 設置關閉窗體上時默認執行的操作
?
??? 布局管理:布置組件在容器中的位置和大小
??? ??? FlowLayout:流式布局管理,Panel和JPanel的默認布局管理就是FlowLayout
??? ??? ??? 三種構造方式:
??? ??? ??? ??? FlowLayout()?
??? ??? ??? ??? ??? 構造一個新的 FlowLayout,居中對齊,默認的水平和垂直間隙是 5 個單位。?
??? ??? ??? ??? FlowLayout(int align)?
??? ??? ??? ??? ??? 構造一個新的 FlowLayout,對齊方式是指定的,默認的水平和垂直間隙是 5 個單位。?
??? ??? ??? ??? FlowLayout(int align, int hgap, int vgap)?
??? ??? ??? ??? ??? 創建一個新的流布局管理器,具有指定的對齊方式以及指定的水平和垂直間隙。?
??? ??? ??? ??? ??? ?
??? ??? BorderLayout:按方位進行布局管理,不明確指定,就會默認加載在中間,Frame和JFrame默認的布局管理器是BorderLayout
??? ??? ??? 兩種構造方式:
??? ??? ??? ??? BorderLayout()?
????????? ??? ??? ??? ??? 構造一個組件之間沒有間距的新邊界布局。?
??? ??? ??? ??? BorderLayout(int hgap, int vgap)?
????????? ??? ??? ??? ??? 用指定的組件之間的水平間距構造一個邊界布局。?
?
??? ??? GridLayout:網格布局,通過行列、間距來用網格分割,把組件放入網格中,先行后列擺放組件。
??? ??? ??? 三種構造方式:
??? ??? ??? ??? GridLayout()?
??? ??? ??? ??? ??? 創建具有默認值的網格布局,即每個組件占據一行一列。?
??? ??? ??? ??? GridLayout(int rows, int cols)?
??? ??? ??? ??? ??? 創建具有指定行數和列數的網格布局。?
??? ??? ??? ??? GridLayout(int rows, int cols, int hgap, int vgap)?
??? ??? ??? ??? ??? 創建具有指定行數和列數的網格布局,并將水平和垂直間距設置為指定值。?
??? ??? ??? ?
??? 組件:圖形界面中所有能看到的
??? ??? JButton :按鈕
??? ??? JTextField:單行文本域
??? ??? JTextArea:多行文本區
??? ??? JLabel:標簽
圖形界面:
??? 布局管理器:
??? ??? CardLayout:卡片布局,面板重疊放置,只能看到一個,最先添加的會被顯示出來,可以進行翻動
??? ??? ??? 兩種構造方法:
??? ??? ??? ??? CardLayout()?
????????? ??? ??? ??? ??? 創建一個間隙大小為 0 的新卡片布局。?
??? ??? ??? ??? CardLayout(int hgap, int vgap)?
????????? ??? ??? ??? ??? 創建一個具有指定的水平和垂直間隙的新卡片布局。?
????????? ??? ??? 常用的方法:
??? ??? ??? ??? previous(Container parent)?
????????? ??? ??? ??? ??? 翻轉到指定容器的前一張卡片。
????????? ??? ??? ??? show(Container parent, String name)?
????????? ??? ??? ??? ??? 翻轉到已添加到此布局的具有指定 name 的組件
????????? ??? ??? ??? next(Container parent)?
????????? ??? ??? ??? ??? 翻轉到指定容器的下一張卡片。
????????? ??? ??? ??? first(Container parent)?
????????? ??? ??? ??? ??? 翻轉到容器的第一張卡片。??? ?
????????? ??? ??? ??? last(Container parent)?
????????? ??? ??? ??? ??? 翻轉到容器的最后一張卡片。
????????? ??? ??? ??? ??? ?
????????? ??? GridBagLayout:增強版的網格布局,組件可以跨行跨列的進行布局。
????????? ??? ??? 構造方法:
????????? ??? ??? ??? GridBagLayout()?
????????? ??? ??? ??? ??? 創建網格包布局管理器。
????????? ??? ??? 注意:
????????? ??? ??? ??? 該布局管理器的具體實現需要借助GridBagConstraints類,利用GridBagConstraints類的屬性對組件進行設置,具體內容查看API文檔。
????????? ??? ??? ??? ?
??? 菜單項:
??? ??? JMenuBar:菜單欄的實現,將JMenu對象添加到菜單欄以構造菜單
??? ??? ??? 構造方法:
??? ??? ??? ??? JMenuBar()?
????????? ??? ??? ??? ??? 創建新的菜單欄。
????????? ??? ??? ??? ??? ?
??? ??? JMenu:菜單的該實現是一個包含JMenuItem的彈出窗口
??? ??? ??? 構造方法:
??? ??? ??? ??? JMenu(String s)?
????????? ??? ??? ??? ??? 構造一個新JMenu,用提供的字符串作為其文本。
????????? ??? ??? ??? ??? ?
??? ??? JMenuItem:菜單中的項的實現,菜單項本質上是位于列表中的按鈕
??? ??? ??? 構造方法:
??? ??? ??? ??? JMenuItem(String text)?
????????? ??? ??? ??? ??? 創建帶有指定文本的JMenuItem。
????????? ??? ??? ??? ?
AWT事件模型:
??? 事件模型的三要素:
??? ??? 事件源(Object):事件的產生者。
??? ??? 事件(EventObject):描述發生了什么事情。??
??? ??? 事件監聽(EventListener):事件的處理者
??? ??? 關系:
??? ??? ??? 事件只與事件源有關,與事件監聽無關
??? ??? ??? 一個事件源可以注冊多個事件監聽。
??? ??? ??? 一個事件監聽器可以在多個事件源中注冊。
??? ??? ??? 一個事件源可以就同一類事件注冊多個事件監聽。
??? ?
??? 事件處理機制:委派式的處理機制(是一種松耦合)
??? ??? 組件自身會產生事件對象,但本身不一定負責處理,而是交給一個監聽者去處理
??? ??? ?
??? 實現監聽的步驟:
??? ??? a. 實現監聽接口implements XxxxListener
??? ??? b. 重寫方法actionPerformed(ActionEvent e)?
??? ??? c. 注冊監聽addXxxxListener(ActionListener l)?
??? ??? ?
??? 適配器:一個重寫了所有接口中方法的類
??? ??? 在java.awt.event包中,會有一些適配器,也就是把相應的XxxxListener,換成XxxxAdapter就是適配器。
??? ??? 在AWT中經常用匿名內部類來繼承適配器做監聽
JFC:java基礎類庫(具體的類可以查看API文檔)
?
觀察者模式:
??? 事件監聽者對事件源進行監聽,事件源會發生某些事件,監聽者需要對事件作出相應的處理。
??? ?
??? 事件監聽者(Observer):??? ?
??? ??? 處理事件
??? ??? ?
??? 事件對象(Observable):
??? ??? 注冊監聽
??? ??? 取消監聽
??? ??? 通知監聽
??? ??? ?
??? 編程步驟:
??? ??? a. 定義一個監聽者,使其實現Observer接口,實現其中的方法update(Observable o, Object arg)。
??? ??? b. 定義一個事件對象,使其繼承Observable類,定義一個產生事件的方法,在方法里去注冊監聽addObserver(Observer o)、標志改變setChanged()(如果不寫,則說明該事件沒有發生,監聽者不會反映)、啟動監聽notifyObservers()。
??? ??? ??? 注意:注冊監聽和標志改變不分先后,但標志改變和啟動監聽是不能互換的。
??? ??? ??? ?
??? 應用:當某事物發生變化,需要采取行動,則可以采用觀察者模式。
??? ?
適配器模式:
??? Adapter適配器模式是一種結構型模式,將兩個互不兼容的類糾合在一起。
??? ?
??? 主要應對:由于應用環境的變化,常常需要將“一些現存的對象”放在新的環境中應用,但是,新環境要求的接口是現存對象所不滿足的。
??? ?
??? 作用:在不改變源代碼的情況下實現需求。
?
java.math.BigDecimal:不可變的、任意精度的有符號十進制數。
??? 必須用String類型進行構造,才能實現精確計算
?
I/O流后面會詳細講解,今天的了解下就可以了。
多線程:
??? 進程與線程:
??? ??? 進程:同一個操作系統中執行的一個子程序,包含了三部分虛擬CPU、代碼、數據
??? ??? 多進程:同一個操作系統中執行的多個并行的子程序。可以提高cpu的使用率
??? ??? 線程:在同一個進程當中執行的子程序流
??? ??? 多線程:同一個進程當中并發執行的多個子程序流。可以提高cpu的使用率
??? ??? 進程與線程的區別:
??? ??? ??? 進程有獨立的進程空間,進程中的數據存放空間(堆空間和棧空間)是獨立的。
??? ??? ??? 線程的堆空間是共享的,棧空間是獨立的,線程消耗的資源也比進程小,相互之間可以影響的。
??? ??? java中如何調進程:
??? ??? ??? 調用本地程序的兩個類
??? ??? ??? ??? Runtime
??? ??? ??? ??? ??? Runtime.getRuntime.exec(...);??? //執行一個程序
??? ??? ??? ??? ??? ??? 其返回值就是Process類型
??? ??? ??? ??? Process??? ??? ?
??? ??? 注意:
??? ??? ??? 只有運行狀態的線程才有機會執行代碼,主線程的中止不會影響其他的正在運行中的線程,主線程中止也就是main()方法退出了。只有進程中的所有線程都中止時,進程(JVM進程)才會退出,只要有線程沒有中止,進程就不會退出。
??? ??? ??? 操作系統決定線程是否有優先級,獨占式的操作系統中系統會有優先級的概念,共享式的操作系統則不會有優先級的。
??? ??? ??? 在線程的內部,程序依然順序執行
??? ?
??? 線程編程的兩種方法:
??? ??? 寫一個類,繼承Thread類,覆蓋Thread類中繼承來的run()方法,這樣就寫好了自定義的線程類。
??? ??? ??? 繼承java.lang.Thread類:
??? ??? ??? ??? class MyThread extends Thread{
??? ?? ??? ??? ??? ??? public void run(){??? ??? //覆蓋run(),線程體方法,自身其實就是普通的方法
??? ?? ??? ??? ??? ??? ??? .......
??? ??? ??? ??? ??? }
??? ??? ??? ??? }
??? ???? ??? 啟動線程:
??? ??? ??? ??? public class TestThread{
??? ? ??? ??? ??? ??? public static void main(){
??? ? ??? ??? ??? ??? ??? Thread t1=new Mythread();
??? ? ??? ??? ??? ??? ??? T1.start();??? ??? //調用start()來啟動線程,線程啟動方法,向線程調度器說明當前線程已經準備好了,是一種可運行狀態
??? ? ??? ??? ??? ??? }
??? ??? ??? ??? }
??? ??? ??? ??? ?
??? ??? 寫一個類,實現Runable接口,實現其中的run()方法。這種方法寫好的類的對象需要作為線程類創建對象時構造方法的參數。
??? ??? ??? 實現java.lang.Runnable接口:
??? ??? ??? ??? Class MyThread? implements Runnable{
??? ??? ? ??? ??? ??? public void run(){
??? ??? ??? ??? ?
??? ??? ? ??? ??? ??? }
??? ??? ??? ??? }
??? ???? ??? 啟動線程:
??? ??? ??? ??? public class TestThread{
??? ??? ??? ??? ??? public static void main(){
??? ??? ??? ??? ??? ??? Runnable myThread = new MyThread();
??? ??? ??? ??? ??? ??? Thread t = new Thread(myThread);
??? ??? ??? ??? ??? ??? t.start();
??? ??? ??? ??? ??? }
??? ??? ??? ??? }
??? ??? ??? ??? ?
??? Thread中的一些方法:
??? ??? currentThread()?
??? ????????? ??? 返回對當前正在執行的線程對象的引用(實現接口方式時使用)
??? ??? sleep(long millis)?
????????? ??? ??? 在指定的毫秒數內讓當前正在執行的線程休眠(暫停執行)。
??? ??? ??? 本線程不會去搶,除非sleep結束。
??? ??? ??? 多個線程之間都會去搶執行權限,不會考慮優先級。
??? ??? yield()?
????????? ??? ??? 暫停當前正在執行的線程對象,并執行其他線程。
????????? ??? ??? 只給本類或者優先級大于本類優先級的線程去搶。
????????? ??? join()?
????????? ??? ??? 等待該線程終止。??? ?
????????? ??? ??? 放在start()前面則沒有用處。
????????? ??? setDaemon(boolean on)?
????????? ??? ??? 將該線程標記為守護線程,守護線程需要依賴其他線程,會在虛擬機停止的時候停止。
??? ??? ????????? ??? ??? ?
??? 線程的生命周期:
??? ??? 1)初始狀態:此時線程只是處于JVM進程中,只是創建了一個線程對象,并沒有真正開始運行。
??? ??? 2)可動行狀態:調用線程對象的start()方法,此時線程才真正的被創建,進入可運行狀態,等待CPU的調度。“萬事俱備,只欠CPU”。
??? ??? 3)運行狀態:正在運行的線程,此時它擁有CPU的執行權。
??? ??? 4)阻塞狀態:運行狀態中的線程,如果正在等待用戶輸入或調用了sleep()和join()等方法都會導致線程進入阻塞狀態,注意從阻塞狀態出來的線程不一定馬上回到運行狀態,而是重新回到可運行狀態,等待CPU的再次調度。
??? ??? 5)等待隊列狀態:一個線程調用一個對象的wait()會自動放棄該對象的鎖標記,進入等待隊列狀態,只有當有另外一線程調用臨界資源的notify()或notifyAll()方法,建議多使用notifyAll(),才會將等待隊列中的線程釋放,此線程進入鎖池狀態。
??? ??? 6)鎖池狀態:每個對象都有互斥鎖標記,以防止對臨界資源的訪問造成數據的不一致,和數據的不完整性。一個線程擁有一個對象的鎖標記后,另一線程想訪問該對象,必須在鎖池中等待。由系統決定哪個線程拿到鎖標記并運行。注意從鎖池狀態出來的線程不是馬上回到運行狀態,而是重新回到可運行狀態,等待CPU的再次調度。
??? ??? 7)終止狀態:一個線程運行結束后稱為終止狀態,一個進程中只有所有的線程退出后才會終止。
多線程:
??? 多線程的同步:??? ?
??? ??? 多線程并發訪問同一個對象(臨界資源),如果不對線程進行同步控制,破壞了原子操作(不可再分的操作),則會造成臨界資源(兩個線程同時訪問的資源)的數據不一致。???
?
??? ??? 每一個對象都有一個互斥的鎖標記和一個鎖池。當線程擁有這個對象的鎖標記時才能訪問這個資源,沒有鎖標記便進入鎖池,保證在同步代碼塊中只有一個線程,解決了多線程同步控制的問題。
??? ??? ?
??? ??? 關鍵字:synchronized??? //線程在同步代碼中必須采用串行訪問
??? ??? ??? synchronized修飾代碼塊:對括號內的對象object加鎖,只有拿到對象鎖標記的線程才能進入該代碼塊。
??? ?? ??? ??? ??? public void push(char c){?
??? ??????? ??? ??? ??? synchronized(object){ ??? //object只要是對象就可以,但必須保證是同一對象
??? ??????? ??? ??? ??? ??? ……
??? ??????? ??? ??? ??? ??? 同步代碼?
??? ??????? ??? ??? ??? ??? ……
??? ??????? ??? ??? ??? }?
??? ?? ??? ??? ??? }
??? ?? ??? ??? ??? ?
??? ??? ??? synchronized修飾方法:在整個方法范圍內對當前對象的加鎖,只有拿到對象鎖標記的線程才能執行該方法。盡可能的少用
??? ?? ??? ??? ??? public synchronized void push(char c) {
??? ??? ??? ??? ??? ……
??? ??? ??? ??? ??? 同步代碼?
??? ??? ??? ??? ??? ……??? ?
??? ??? ??? ??? }
??? ????? ??? ??? ??? ?
??? ??? 一個線程可以同時擁有多個對象的鎖標記,鎖標記如果過多,就會出現線程等待其他線程釋放鎖標記,而又都不釋放自己的鎖標記供其他線程運行的狀況,造成死鎖。??? ??? ??? ??? ?
?
??? ??? 靜態方法可以是同步方法:但是它所鎖的并不是當前對象,是類對象。
??? ??? 抽象方法不能是synchronized同步的方法。
??? ??? 構造方法不能是synchronized同步的方法。
??? ??? ??? ?
??? ??? 線程因為未拿到鎖標記而發生阻塞進入鎖池(lock pool)。每個對象都有自己的一個鎖池的空間,用于放置等待運行的線程。由系統決定哪個線程拿到鎖標記并運行
??? ??? ?
??? ??? 利用Collections類中的synchronizedXxxx(Xxxx ss)方法可以得到相應集合的線程安全的集合
??? ??? ?
??? ??? 注意:
??? ??? ??? 在同步語句塊中不能直接操作對象鎖正在使用的對象。
??? ??? ??? 對象與鎖一一對應。
??? ??? ??? 同步依賴對象鎖,鎖對象相同,同步語句串行,鎖對象不同,同步語句并行。
??? ??? ??? 順序鎖,不要回調,反向打開。
??? ??? ??? 能不用同步就不用同步,有數據共享沖突時才使用同步。
??? ??? ?
??? 等待通知機制:
??? ??? 線程間通信使用的空間稱之為對象的等待對列(wait pool),該隊列也是屬于對象的空間的。
??? ??? ?
??? ??? 使用Object類中wait()的方法,在運行狀態中,線程調用wait(),此時表示線程將釋放自己所有的鎖標記和CPU的占用,同時進入這個對象的等待池。等待池的狀態也是阻塞狀態,只不過線程釋放自己的鎖標記。只有在對該對象加鎖的同步代碼塊里,才能掉用該對象的wait(),表示線程將會釋放所有鎖標記,進入等待隊列,線程將進入等待隊列狀態。
??? ??? ?
??? ??? 一個線程進入了一個對對象加鎖的同步代碼塊,并對該對象調用了wait()方法,釋放自己擁有的所有鎖標記,進入該對象等待隊列,另一個線程獲得了該對象的鎖標記,進入代碼塊對該對象調用了notify()方法,就會從等待隊列里釋放出一線程,釋放出的這個線程要繼續運行就還要進入那個同步代碼塊,因為得不到要訪問代碼塊對象的鎖標記,而進入該對象的鎖池,等待鎖標記釋放。
??? ??? ?
??? ??? 什么情況下釋放鎖:
??? ??? ??? 同類代碼執行完畢。
??? ??? ??? 異常未處理,錯誤退出。
??? ??? ??? 調用wait()。
??? ??? ?
??? ??? 相關方法:
??? ??? ??? 1) wait():交出鎖和CPU的占用;?
??? ??? ??? 2) notify():將從對象的等待池中移走一個任意的線程,并放到鎖池中,那里的對象一直在等待,直到可以獲得對象的鎖標記。?
??? ??? ??? 3) notifyAll(): 將從等待池中移走所有等待那個對象的線程并放到鎖池中,只有鎖池中的線程能獲取對象的鎖標記,鎖標記允許線程從上次因調用wait()而中斷的地方開始繼續運行
??? ??? ??? ?
??? ??? 注意:
??? ??? ??? 用notifyAll()取代notify(),因為在調用notify()方法時,是由系統決定釋放出哪個線程。
??? ??? ??? 只能對加鎖的資源進行wait()和notify()。
??? ??? ??? 判斷是否進行等待wait()時,用while代替if來進行判斷。
??? ??? ??? ?
I/O流
??? 字節輸入流:InputStream類為所有字節輸入流的父類
??? ??? 三個基本的read()方法:?
??? ????? ??? ??? int read()
??? ????? ??? ??? ??? 從流里讀出的一個字節。不推薦使用
??? ????? ??? ??? int read(byte[] b)
??? ????? ??? ??? ??? 將數據讀入到字節數組中,并返回所讀的字節數
??? ????? ??? ??? int read(byte[] b, int off, int len)
??? ????? ??? ??? ??? off? 從哪里開始讀。
??? ????? ??? ??? ??? len? 讀取多少。
??? ????? ??? ??? ??? 將輸入流中最多 len 個數據字節讀入字節數組。
??? ??? 其它方法:?
??? ????? ??? ??? void close()?
??? ????? ??? ??? ??? 關閉此輸入流并釋放與該流關聯的所有系統資源。
??? ????? ??? ??? int available()
??? ????? ??? ??? ??? 返回不受阻塞地從此輸入流讀取的字節數。
??? ????? ??? ??? long skip(long n)
??? ????? ??? ??? ??? 跳過和放棄此輸入流中的n個數據字節,該方法有可能失效。
??? ????? ??? ??? boolean markSupported()
??? ????? ??? ??? ??? 測試此輸入流是否支持 mark 和 reset 方法。
??? ????? ??? ??? void mark(int n)
??? ????? ??? ??? ??? 在此輸入流中標記當前的位置
??? ????? ??? ??? void reset()
??? ????? ??? ??? ??? 將此流重新定位到對此輸入流最后調用 mark 方法時的位置。?
?
??? 字節輸出流:OutputStream類是所有字節輸入流的父類
??? ??? 三個基本的write()方法:?
??? ??? ??? void write(int n)
??? ??? ??? ??? 將指定的字節寫入此輸出流。
??? ??? ??? void write(byte[] b)?
??? ??? ??? ??? 將 b.length 個字節從指定的字節數組寫入此輸出流。
??? ??? ??? void write(byte[] b, int off, int len)
??? ??? ??? ??? 將指定字節數組中從偏移量off開始的len個字節寫入此輸出流。
??? ??? 其它方法:?
??? ??? ??? void close()
??? ??? ????? ??? ??? 關閉此輸出流并釋放與此流有關的所有系統資源。
??? ??? ??? void flush()
??? ??? ????? ??? ??? 刷新此輸出流并強制寫出所有緩沖的輸出字節。?
??? ??? ????? ??? ??? ?
??? 文件輸入輸出流:FileInputStream和FileOutputStream
??? ??? 要構造一個FileInputStream,所關聯的文件必須存在而且是可讀的。
??? ??? ??? 如:
??? ??? ??? ??? FileInputStream fis = new FileInputStream("myfile.dat");?
??? ??? 要構造一個FileOutputStream,而輸出文件已經存在,則它將被覆蓋。??? ??? ???? ?
??? ??? ??? 如:??? ??? ??? ?
??? ??? ?? ??? ??? FIleOutputStream fos = new FileOutputStream("results.dat");?
??? ??? ?? ??? 要想以追加的方式寫,則需要一個額外的參數,如:
??? ??? ??? ??? FileOutputStream outfile = new FileOutputStream("results.dat" ,true);??? //參數為true時輸出為追加,為false時為覆蓋。?
I/O流
??? 流的概念:程序與數據來源之間的橋梁
??? ?
??? 流的分類:
??? ??? 按數據方向分:輸入流和輸出流
??? ??? ??? ?輸入流:InputStream/Reader
??? ??? ??? ?OutputStream/Writer
??? ??? 按數據類型分:字節流和字符流
??? ??? ??? 字節流:InputStream/OutputStream
??? ??? ??? 字符流:Reader/Writer
??? ??? 按流的功能分:節點流和處理流
??? ??? ??? 節點流用操作數據的來源。
??? ??? ??? 處理流用來封裝節點流,從而給節點流增加一個功能,不能獨立存在,在關閉流時如果使用了處理流,只需關閉最外層的流就可以了。
??? ??? ??? 區分節點流和處理流的小方法:
??? ??? ??? ??? 看構造器,節點流參數為數據來源,而處理流參數為其他流。
??? ?
??? 選擇流的思路:
??? ??? 先考慮是輸入流還是輸出流,
??? ??? 再考慮是字節流還是字符流,
??? ??? 最后考慮是節點流還是處理流。
??? ??? ?
??? 字符流:Reader和Writer所有字符流的父類型
??? ??? Java技術使用Unicode來表示字符串和字符,而且提供16位版本的流,以便用類似的方法處理字符。?
??? ??? 如果構造了一個連接到流的Reader和Writer,轉換規則會在使用缺省平臺所定義的字節編碼和Unicode之間切換。?
??? ??? ?
??? 橋梁流:InputStreamReader和OutputStreamWriter(字節流轉化成字符流的橋轉換器)
??? ??? 這兩個類不是用于直接輸入輸出的,他是將字節流轉換成字符流的橋轉換器,并可以指定編解碼方式。
??? ??? ??? ?
??? 逐行讀寫流:BufferedReader/BufferedWriter
??? ??? 以上兩個都是過濾流,需要用其他的節點流來作參數構造對象。
??? ??? BufferedReader的方法:readLine():String ,當他的返回值是null時,就表示讀取完畢了。要注意,再寫入時要注意寫換行符,否則會出現阻塞。
??? ??? BufferedWriter的方法:newLine() ,這個方法會寫出一個換行符。
??? ??? ?
??? 管道流:線程交互的時候使用
??? ??? PipedInputStream/PipedOutputStream
??? ??? ??? 傳送輸出流可以連接到傳送輸入流,以創建通信管道。傳送輸出流是管道的發送端。通常,數據由某個線程寫入 PipedOutputStream 對象,并由其他線程從連接的 PipedInputStream 讀取。
??? ??? 注意:管道輸出流和管道輸入流需要對接。
??? ??? ??? ?
??? 數據流:DataInputStream和DataOutputStream
??? ??? 通過流來讀寫Java基本類,注意DataInputStream和DataOutputStream的方法是成對的。?
??? ??? 支持直接輸出輸入各種數據類型。
??? ??? 注意:使用DataOutputStream/DataInputStream時,要注意寫入順序和讀取順序相同,否則會將沒有分割寫入的信息分割不正確而讀取出錯誤的數據。
??? ??? ?
??? Properties類:針對屬性文件(*.properties,內容是name=value)進行操作,在java.util包下??? ?
??? ??? load(InputStream inStream)?
????????? ??? ??? 從輸入流中讀取屬性列表(鍵和元素對)。
????????? ??? getProperty(String key)?
????????? ??? ??? 用指定的鍵在此屬性列表中搜索屬性。
??? ?
??? java編碼方式:
??? ??? 編碼:把字符轉換成數字存儲到計算機中,按ASCII將字母映射為整數。
??? ??? 解碼:把數字從計算機轉換成相應的字符的過程。??? ?
??? ??? ?
??? ??? 不同的國家有不同的編碼,當編碼方式和解碼方式不統一時,產生亂碼。
??? ??? 因為美國最早發展軟件,所以每種的編碼都向上兼容ASCII 所以英文沒有亂碼。
??? ??? ??? ASCII(英文)??? ??????????????? 1個字符占一個字節(所有的編碼集都兼容ASCII)
??? ??? ??? ISO8859-1(拉丁文)? ??? ? 1個字符占一個字節
??? ??? ??? GB-2312/GBK??????? ??? ??? ? 1個字符占兩個字節(多用于中文)
??? ??? ??? Unicode??????????? ??? ??? ? 1個字符占兩個字節(網絡傳輸速度慢)
??? ??? ??? UTF-8????????????? ??? ??? ? 變長字節,對于英文一個字節,對于漢字兩個或三個字節。
??? ??? ??? ?
??? ??? 中文編碼時出現亂碼的情況:
??? ??? ??? 用流操作文件。
??? ??? ??? 網頁(動態靜態)。
??? ??? ??? 網絡傳遞消息。
??? ??? ??? ?
??? ??? 解決亂碼的方式:
??? ??? ??? String temp = 亂碼的字符串
??? ??? ??? temp = new String(temp.getBytes("ISO8859-1") , "GBK")???
??? ??? ??? ??? 將temp按照ISO8859-1的方式進行解碼生成一個字節序列,然后在按照GBK的方式解碼字節序列生成字符串。
??? ??? ?
??? File類:可表示文件或者目錄
??? ??? File下的方法是對磁盤上的文件進行磁盤操作,但是無法讀寫文件的內容。
?
??? ??? 構造器:
??? ??? ??? File(String pathname)??? //以文件的路徑做參數
??? ??? ??? ?
??? ??? File類的方法:
??? ??? ??? boolean createNewFile()?
??? ??? ??? ??? 創建一個新文件
??? ??? ??? File createTempFile(String prefix, String suffix, File directory)?
?????????? ??? ??? ??? 在指定目錄中創建一個新的空文件,使用給定的前綴和后綴字符串生成其名稱。會在前綴和后綴之間加一個隨機數?
??? ??? ??? boolean mkdir()
??? ??? ??? ??? 創建一個新目錄
??? ??? ??? boolean delete()
??? ??? ??? ??? 刪除文件,刪除的是創建File對象時指定與之關聯創建的那個文件。
??? ??? ??? String[] List()
??? ??? ??? ??? 返回當前File對象下所有顯文件和目錄名(相對路徑)
??? ??? ??? File[] ListFiles()
??? ??? ??? ??? 返回當前File對象(必須是目錄)下的所有File對象,可以用getName()來訪問到文件名。
??? ??? ??? boolean isDirectory()和boolean isFile()
??? ??? ??? ??? 判斷究竟是目錄還是文件。
??? ??? ??? boolean exists()?
??? ??? ??? ??? 判斷文件或文件夾是否存在。
??? ??? ??? String getPath()
??? ??? ??? ??? 獲得相對路徑。
??? ??? ??? String getAbsolutePath()
??? ??? ??? ??? 獲得文件的絕對路徑
??? ??? ?
??? ??? 注意:
??? ??? ??? File類的對象實施表示一個文件并不是真正的文件,只是一個代理而已,通過這個代理來操作文件
??? ??? ??? 創建一個文件對象和創建一個文件在java中是兩個不同的概念。前者是在虛擬機中創建了一個文件,但卻并沒有將它真正地創建到OS的文件系統中,隨著虛擬機的關閉,這個創建的對象也就消失了。而創建一個文件才是在系統中真正地建立一個文件。
??? ??? ??? 例如:
??? ??? ??? ??? File f=new File(“11.txt”);??? //創建一個名為11.txt的文件對象
??? ??? ??? ??? f.CreateNewFile();???? ??? //真正地創建文件
?
??? RandomAccessFile:?
??? ??? 允許隨機訪問文件,類支持直接輸出輸入各種數據類型。
??? ??? ?
??? ??? 構造器:
??? ??? ??? RandomAccessFile(File file, String mode)?
????????? ??? ??? ??? 創建從中讀取和向其中寫入(可選)的隨機存取文件流,該文件由 File 參數指定。?
??? ??? ??? RandomAccessFile(String name, String mode)?
????????? ??? ??? ??? 創建從中讀取和向其中寫入(可選)的隨機存取文件流,該文件具有指定名稱。?
??? ??? ??? ??? mode( r:以只讀方式打開????? rw:可讀可寫,不存在則創建)
?
??? ??? 相關方法:
??? ??? ??? long getFilePointer()
??? ??? ??? ??? 返回文件指針的當前位置。?
??? ??? ??? void seek(long pos)
??? ??? ??? ??? 設置文件指針到給定的絕對位置。?
??? ??? ??? long length()
??? ??? ??? ??? 返回文件的長度。??? ??? ??? ?
??? ??? ??? ??? ?
??? 對象流:ObjectInputStream和ObjectOutputStream(實現對象序列化)
??? ??? 對象流是過濾流,需要節點流作參數來構造對象,用于直接把對象寫入文件和從文件中讀取對象。
??? ??? 只有實現了Serializable接口的類型的對象才可以被讀寫,Serializable接口是個標記接口,其中沒有定義方法。
??? ??? 對象會序列化成一個二進制代碼,文件中保存對象的屬性。
??? ??? ?
??? ??? writeObject(o)、readObject()這兩個是對象讀寫操作時用的方法。
??? ??? ??? Object o = new Object();??? ?
??? ??? ??? FileOutputStream fos=new FileOutputStream("Object.txt");
??? ??? ??? ObjectOutputStream oos=new ObjectOutputStream(fos);
??? ??? ??? oos.writeObject(o);
??? ??? ??? oos.close();
?
??? ??? ??? FileInputStream fis =new FileInputStream(“Object.txt”);
??? ??? ??? ObjectInputStream ois =new ObjectInputStream(fis);
??? ??? ??? Object o = (Object)Ois.readObject();
??? ??? ??? ois.close();
?
??? ??? 一個類中有其他類型的對象,那么,這個類實現了Serializable接口,在對象序列化時,也同樣要求這個類中屬性都能夠對象序列化(基本類型除外)。
??? ??? ?
??? ??? 注意:
??? ??? ??? 對于對象流的操作,在寫對象時要一次寫入完畢,如果使用追加模式寫入,只會讀取到上一次寫入的對象,使用對象流寫入時,會先寫入一個頭部,然后寫入數據,最后加上結束符號,如果使用追加方式寫入的話,那就會在結束符號繼續向下寫入,但是在讀取時只會讀到結束符為止,以后再次寫入的數據就會丟失。
?
??? ??? ??????
I/O流
??? 對象流:ObjectInputStream和ObjectOutputStream
??? ??? 對象流是過濾流,需要節點流作參數來構造對象,用于直接把對象寫入文件和從文件中讀取對象。
??? ??? 只有實現了Serializable接口的類型的對象才可以被讀寫,Serializable接口是個標記接口,其中沒有定義方法。
??? ??? 對象會序列化成一個二進制代碼。
??? ??? ?
??? ??? writeObject(o)、readObject()這兩個是對象讀寫操作時用的方法。
??? ??? ??? Object o = new Object();??? ?
??? ??? ??? FileOutputStream fos=new FileOutputStream("Object.txt");
??? ??? ??? ObjectOutputStream oos=new ObjectOutputStream(fos);
??? ??? ??? oos.writeObject(o);
??? ??? ??? oos.close();
?
??? ??? ??? FileInputStream fis =new FileInputStream("Object.txt");
??? ??? ??? ObjectInputStream ois =new ObjectInputStream(fis);
??? ??? ??? Object o = (Object)ois.readObject();
??? ??? ??? ois.close();
??? ??? ?
??? ??? transient只能用來修飾屬性。表示這個屬性在對象序列化時將被忽略。
??? ??? ??? transient int num;
??? ??? ??? 表示當我們進行序列化時忽略這個屬性。
?
??? ??? 注意:
??? ??? ??? 對于對象流的操作,在寫對象時要一次寫入完畢,如果使用追加模式寫入,只會讀取到上一次寫入的對象。使用對象流寫入時,會先寫入一個頭部,然后寫入數據,最后加上結束符號,如果使用追加方式寫入的話,那就會在結束符號繼續向下寫入,但是在讀取時只會讀到結束符為止,以后再次寫入的數據就會丟失。
??? ??? ??? 包名、類名和屬性可以被序列化,方法和構造器不會被序列化的。
??? ??? ??? 靜態屬性不會被序列化的。
??? ??? ??? 屬性會被遞歸序列化的,也就是一個類中有引用類型的屬性,如果這個屬性對應的類實現了Serializable接口,在對象序列化時,也同樣會對這個類中的屬性進行對象序列化,如果沒有實現Serializable接口,則會拋出異常。
??? ??? ??? 所有屬性必須都是可序列化的,特別是當有些屬性本身也是對象的時候,要尤其注意這一點。
??? ??? ??? 網絡中傳遞對象必須實現序列化。??? ?
??? ?
nio無阻塞的I/O(優化的I/O)??? ?
??? java.nio?? 定義塊
??? ??? Buffer類:一種用于特定的基本類型數據的容器
??? ??? ??? 緩沖:就是塊,用來存儲內容。
??? ??? ??? 容量:內存開辟的大小,根據類型的不同,有不同的空間。
??? ??? ??? 界限:可用部分,即不應讀取或寫入的第一個元素的索引。
??? ??? ??? 位置:當前指針的位置,從0開始。??? ?
??? ??? ??? 容量>=界限>=位置
??? ??? ??? ??? ?
??? ??? ??? 相關方法:
??? ??? ??? ??? int capacity()?
????????? ??? ??? ??? ??? 返回此緩沖區的容量。?
????????? ??? ??? ??? int limit()?
????????? ??? ??? ??? ??? 返回此緩沖區的界限。?
????????? ??? ??? ??? int position()?
????????? ??? ??? ??? ??? 返回此緩沖區的位置。?
????????? ??? ??? ??? Buffer flip()?
????????? ??? ??? ??? ??? 相當于截斷沒有用的空間,然后把指針移向開頭,使limit=position,position=0
????????? ??? ??? ??? Buffer position(int newPosition)?
????????? ??? ??? ??? ??? 設置此緩沖區的位置。?
????????? ??? ??? ??? ??? ?
??? ??? ??? 當有大的文件需要處理的時候,為了不影響性能建議用直接緩沖。
??? ??? ??? Buffer有直接緩沖和間接緩沖兩種。
??? ??? ??? 只有ByteBuffer類提供了直接緩沖。使用直接緩沖,不影響程序。其它類想用直接緩沖需要進行轉換。
??? ??? ?
??? java.nio.channels??? 對塊進行讀寫的通道,類似于以前的流
??? ??? Channel接口:用于 I/O 操作的連接
??? ??? ?
??? ??? 編程步驟:
??? ??? ??? a. 先創建一個I/O流,
??? ??? ??? b. 使用I/O流.getChannel()方法,獲得通道,
??? ??? ??? c. 創建大小合適的ByteBUffer,
??? ??? ??? d. 通道的對象.read(buffer)/write(buffer)進行讀寫,
??? ??? ??? e. 關閉所有的流和通道,
??? ??? ??? f. 如果有多線程并發,可以使用"通道.lock()"獲得FileLock對象,用FileLock.release() 釋放此鎖定。
??? ??? ??? g. 當遇到編碼問題,使用CharSet、CharsetDecoder、CharsetEncoder三個類去解決
??? ??? ??? ?
??? ??? 注意:
??? ??? ??? 在讀之前需要調用一下clear()方法,幫助讀操作清理緩沖;寫之前需要調用flip()方法,幫助寫操作清理緩沖。
??? ?
??? java.nio.charset??? 字符集,進行編碼解碼??? ??? ?
??? ??? Charset類:編碼類,編碼的信息
??? ??? ??? forName(String charsetName)
??? ??? ??? ??? 生成一個CharSet實例。
??? ??? ??? decode(ByteBuffer bb)?
????????? ??? ??? ??? 將此 charset 中的字節解碼成 Unicode 字符的便捷方法。
????????? ??? ??? encode(CharBuffer cb)?
????????? ??? ??? ??? 將此 charset 中的 Unicode 字符編碼成字節的便捷方法。
????????? ??? ??? ??? ?
??? ??? CharsetDecoder類:解碼器
??? ??? ??? 能夠把特定 charset 中的字節序列轉換成 16 位 Unicode 字符序列的引擎。
??? ??? ??? ?
??? ??? CharsetEncoder類:編碼器,編碼的行為
??? ??? ??? 能夠把 16 位 Unicode 字符序列轉換成特定 charset 中字節序列的引擎。
?
網絡編程:
??? 網絡基礎知識
??? ??? Mac地址:每個網卡專用地址,也是唯一的。
??? ??? 端口(port):應用程序(進程)的標識(網絡通信程序)
??? ??? ??? OS中可以有65536(2^16)個端口,進程通過端口交換數據。
??? ??? ??? 端口是一種抽象的軟件結構,與協議相關:TCP的23端口和UDT的23端口為兩個不同的概念。
??? ??? ??? 端口應該用1024以上的端口,以下的端口都已經設定功能。
??? ??? 協議:為了進行網絡中的數據交換而建立的約定,協議是為了保證通信的安全,不同層的協議是完全不同的。
??? ??? ??? TCP協議:傳輸層的協議,重發一切錯誤的信息
??? ??? ??? IP協議:保證地址和主機一一對應(ip地址+網卡地址)
??? ??? ??? ?
??? TCP編程:
??? ??? TCP是一種面向連接的保證可靠傳輸的協議。通過TCP協議傳輸,得到的是一個順序的無差錯的數據流。發送方和接收方的成對的兩個socket之間必須建立連接,以便在TCP協議的基礎上進行通信,當一個socket(通常都是server socket)等待建立連接時,另一個socket可以要求進行連接,一旦這兩個socket連接起來,它們就可以進行雙向數據傳輸,雙方都可以進行發送或接收操作。
??? ??? ??? 1) 服務器分配一個端口號,服務器使用accept()方法等待客戶端的信號,信號一到打開socket連接,從socket中取得OutputStream和InputStream。
??? ?? ??? ??? 2) 客戶端提供主機地址和端口號使用socket端口建立連接,得到OutputStream和InputStream。?
?
??? ??? Server端編碼的步驟:
??? ??? ??? 1、new ServerSocket 打開端口
??? ??? ??? 2、調ServerSocket的accept()等待客戶連接,當連接成功返回交互的Socket。
??? ??? ??? 3、調用Socket.getInputStream,getOutputStream獲得服務器端的IO流
??? ??? ??? 4、用處理流封裝后與客戶端交互,記住你讀我寫,一讀一寫。
??? ??? ??? 5、關閉單一客戶端調用Socket的close(),關閉服務器調ServerSocket的close();
?
??? ??? Socket端編碼步驟:
??? ??? ??? 1、new Socket(Server ip,Server port)試圖連接,如成功才有對象
??? ??? ??? 2、調用Socket.getInputStream,getOutputStream獲得服務器端的IO流
??? ??? ??? 3、用處理流封裝后與客戶端交互,記住你讀我寫,一讀一寫。
??? ??? ??? 4、關閉,只有Socket的close()方法。
?
??? 網絡編程:
??? 多線程+網絡:
??? ??? 1、服務器端的等待客戶連接代碼( while(true) ),服務器端與單個客戶端交互的代碼放入線程體( run )
??? ??? 2、客戶端如有其他要求,與服務器交互的代碼也要放入線程體
??? ??? 3、ServerSocket和Socket編碼基于TCP/IP協議,重發一切錯誤數據,當網絡不好時會使性能很差
??? ??? 4、Server端
??? ??? ??? new ServerSocket啟動等待連接線程
??? ??? ??? 在accept后啟動交互線程
??? ??? 注意:交互時注意對應產生,讀寫流對應和次數對應
??? ??? ?
??? URL:網址,統一資源定位器
??? ??? 常用的構造器:
??? ??? ??? URL(String spec)?
??? ??? ??? ??? spec? 一個完整的網址(協議+網址)
????????? ??? ??? ??? 根據 String 表示形式創建 URL 對象。
????????? ??? ??? ??? ?
??? URLConnection:與網址進行連接
??? ??? 通過URL的openConnection()方法生成一個URLConnection實例,通過下面兩個方法,進行流的操作
??? ??? ??? getInputStream()?
??? ????????? ??? ??? 返回從此打開的連接讀取的輸入流
??? ????????? ??? getOutputStream()?
??? ????????? ??? ??? 返回寫入到此連接的輸出流。
??? ????????? ??? ??? ?
??? UDP編程:這種信息傳輸方式相當于傳真,信息打包,在接收端準備紙
??? ??? 特點:
??? ??? ??? 1、一種無連接協議,速度快
??? ??? ??? 2、不保證數據的完整,不會進行重發
??? ??? ??? ?
??? ??? DatagramSocket和DatagramPacket類:
??? ??? ??? DatagramSocket:此類表示用來發送和接收數據報包的套接字。
??? ??? ??? DatagramPacket:數據報包,是UDP下進行傳輸數據的單位,數據存放在字節數組中,其中包括了目標地址和端口以及傳送的信息。
??? ??? ??? ??? 用于接收:??? ?
??? ??? ??? ??? ??? DatagramPacket(byte[] buf , int length)
??? ??? ??? ??? 用于發送:??? ?
??? ??? ??? ??? ??? DatagramPacket(byte[] buf , int length , InetAddress address , int port )
??? ??? ??? ??? ??? ?
??? ??? UDP發送端:
??? ??? ??? 1、創建一個DatagramSocket,不需要參數
??? ??? ??? 2、創建一個DatagramPacket,指明接收方的IP地址和端口號
??? ??? ??? 3、發送數據send(DatagramPacket p)
??? ??? ??? 4、關閉DatagramSocket
?
??? ??? UDP接收端:
??? ??? ??? 1、創建一個DatagramSocket,指定接收方的IP地址和端口號
??? ??? ??? 2、創建一個DatagramPacket,不需要IP地址和端口號
??? ??? ??? 3、接收數據receive(DatagramPacket p)
??? ??? ??? 4、關閉DatagramSocket
??? ??? ??? ?
常用類庫:
??? java.lang.*:
??? ??? System 系統
??? ??? Object 對象
??? ??? ??? clone()
??? ??? ??? equals()
??? ??? ??? hashCode()
??? ??? ??? toString()
??? ??? Class? 類??? ??? ??? ?
??? ??? String/StringBuffer/StringBuilder? 與字符串相關的
??? ??? Thread 線程
??? ??? 所有的封裝類
?
??? java.util.*:
??? ??? Set--->HashSet,TreeSet??? ???
??? ??? List--->ArrayList??? ?
??? ??? Map--->HashMap(線程安全,不支持空),HashTable(線程不安全,支持空)
??? ??? Collections--->外同步
??? ??? Properties
??? ??? Date
??? ??? 觀察者-->Observable,接口Observer
??? ??? 數據結構+工具類
?
??? java.sql.*: 后面馬上會講到,JDBC
??? ?
??? java.awt/swing.*:沒什么機會用到
??? ??? ?
??? java.io.*:? 流相當的多
??? ??? File/FilenameFilter
??? ??? Serializable 對象序列化接口
?
??? ??? ??? 注意:寫一個類要考慮的事情:1、無參構造器,2、實現序列化接口,3、重寫equals,hashCode
??? ??? ?
??? ??? FileInputStream
??? ??? FileOutputStream
??? ??? InputStreamReader
??? ??? PrintStream
??? ??? BufferedReader
??? ??? nio包
??? ?
??? java.net.*:? 以后JSP,Servlet用的時候這個包都已經寫好了
??? ??? InetAddress--->IP地址
??? ??? URL----------->網址
??? ??? URLConnection---->連接
??? ??? ServerSocket,Socket----TCP/IP
??? ??? DatagramSocket,DatagramPacket----UDP
??? ??? ?
??? 一些零散的類:
??? ??? Comparable(可比較的),Comparator(比較器)
?
??? ??? java.math.*;數字在商業軟件中應用時找這個包
??? ??? ??? BigDecimal
??? ??? ?
??? ??? 與反射相關的:java.lang.reflect:? 用的機會比較少
??? ??? ??? ??? ??? ?
??? ??? Runtime(運行環境),Process(進程) ,這兩個在java.lang包里,用了這些就不能跨平臺了,而且效率低