第五章
-
對于HTTP的POST請求方式,使用者送出的表單資料位于HTTP請求的哪一部分?(B)
A 請求頭中
B 請求正文中
資源表示在請求主體中發送,放在首部後面。也就是說,它會按順序發送以下4項:
(1)一個起始行,包括方法、路徑和查詢字元串,以及HTTP版本。
(2)一個HTTP首部。
(3)一個空行(兩個連續的回車/換行對)。
(4)請求正文。
例如,下面這個POST請求向伺服器發送表單資料:
POST /cgi-bin/register.pl HTTP 1.0 Date: Sun, 27 Apr 2013 12:32:36 Host: www. cafeaulait. org Content-type: application/x-WWW- form-urlencoded Content -length: 54 username=Elliotte+Harold&email =elharo%4oibiblio. org
在這個例子中,主體包含一個application/x www-form -urlencoded資料,但并不隻有這一種可能。一般來講,主體可以包含任意的位元組。不過,HTTP首部要包括兩個字段來指定主體的性質:
一個Content-length字段,指定主體中有多少位元組(前面的例子中為54位元組)。
一個Content-type字段,指定類型的MIME媒體類型(前面的例子中内容類型為application/x-www-form-urlencoded)。
java網絡程式設計5、6章習題解析第五章第六章下一節: java網絡程式設計7、8、9習題解析 -
HTTP請求中的請求頭與請求正文之間必須以空行隔開,同樣,HTTP響應中的響應頭與響應正文之間也必須以空行隔開。這句話是否正确?(A)
A 正确
B 不正确
http響應格式
HTTP應答與HTTP請求相似,HTTP響應也由3個部分構成,分别是:
(1)狀态行
(2)響應頭(Response Header)
(3)空格
(4)響應正文
在接收和解釋請求消息後,伺服器會傳回一個HTTP響應消息。
狀态行由協定版本、數字形式的狀态代碼、及相應的狀态描述,各元素之間以空格分隔。
java網絡程式設計5、6章習題解析第五章第六章下一節: java網絡程式設計7、8、9習題解析 -
在HTTP響應結果中,哪個狀态代碼表示響應成功?(C)
A 404
B 305
C 200
D 500
200~299的狀态碼表示成功
300~399的狀态碼指資源重定向
400~499的狀态碼指用戶端請求出錯
500~599的狀态碼指服務端出錯
-
ServerSocket與Socket都有一個SO_TIMEOUT選項,它們的作用是否相同?(B)
A 相同
B 不同
ServerSocket中,SO_TIMEOUT:表示等待客戶連接配接的逾時時間。
Socket中,SO_TIMEOUT:表示接收資料時的等待逾時時間。
- 對于以下程式代碼:
ServerSocket serverSocket=new ServerSocket(8000); serverSocket.setReuseAddress(true);
哪個說法是正确的?(C)
A 以上代碼運作時出錯
B 以上代碼編譯時出錯
C 以上代碼盡管編譯和運作不會出錯,但對SO_REUSEADDR選項的設定無效
D 以上說法都不正确
SO_REUSEADDR:表示是否允許重用伺服器所綁定的位址,應該在綁定在任何端口之前設定。此題已經在SO_REUSEADDR之前綁定了端口,是以設定無效。
改寫:
ServerSocket serverSocket=new ServerSocket(); serverSocket.setReuseAddress(true); //設定ServerSocket的選項 serverSocket.bind(new InetSocketAddress(8000)); //與8000端口綁定
-
如何判斷一個ServerSocket已經與特定端口綁定,并且還沒有被關閉? (B)
A boolean isOpen=serverSocket.isBound();
B boolean isOpen=serverSocket.isBound() && !serverSocket.isClosed();
C boolean isOpen=serverSocket.isBound() && serverSocket.isConnected();
D boolean isOpen=!serverSocket.isClosed();
(1)測試一個ServerSocket是否被關閉:isClosed()
(2)測試一個ServerSocket是否綁定到過某個端口上:isBound()
(3)測試一個ServerSocket是否打開
public static Boolean isOpen(ServerSocket ss){ return ss.isBound()&& !ss.isClosed(); }
-
關于ServerSocket構造方法的backlog參數,以下哪些說法是正确的?(ABCDF)
A backlog參數用來顯式設定作業系統中的連接配接請求隊列的長度。
B 如果沒有設定backlog參數,那麼連接配接請求隊列的長度由作業系統決定。
C 當伺服器端的連接配接請求隊列已滿,用戶端就無法建立與伺服器的連接配接。
D 如果backlog參數的值大于作業系統限定的隊列的最大長度,那麼backlog參數被忽略。
E 連接配接請求隊列直接由ServerSocket建立并管理。
F ServerSocket的accept()方法從連接配接請求隊列中取出連接配接請求。
serverSocket = new ServerSocket(port,3); //連接配接請求隊列的長度為3
ServerSocket構造方法的backlog參數用來顯式設定連接配接請求隊列的長度,它将覆寫作業系統限定的隊列的最大長度(一般為50)。
在以下幾種情況,仍然會采用作業系統限定的隊列的最大長度:
(1)backlog參數的值大于作業系統限定的隊列的最大長度。
(2)backlog參數的值小于或等于0。
(3)在ServerSocket構造方法中沒有設定backlog參數。
管理客戶連接配接請求的任務是由作業系統來完成的。作業系統把這些連接配接請求存儲在一個先進先出的隊列中。許多作業系統限定了隊列的最大長度,一般為50。當隊列中的連接配接請求達到了隊列的最大容量時,伺服器程序所在的主機會拒絕新的連接配接請求。隻有當伺服器程序通過ServerSocket的accept()方法從隊列中取出連接配接請求,使隊列騰出空位時,隊列才能繼續加入新的連接配接請求。
小結:
-
HTTP互動的基本過程
用戶端與伺服器的80端口(或其它端口)連接配接TCP連接配接
用戶端向伺服器發送HTTP請求(Request)
務器向用戶端發送HTTP響應(Response)
伺服器關閉TCP連接配接
-
注意:
HTTP協定是無狀态的
一個Request對應且隻對應一個Response
Response是被動的
-
實作并發伺服器的三種方式:
(1)為每個客戶配置設定一個工作線程。
(2)利用JDK的Java類庫中現成的線程池,由它的工作線程來為客戶服務。
(3)采用非阻塞的方式來實作伺服器。
- 為每個客戶配置設定一個線程
java網絡程式設計5、6章習題解析第五章第六章下一節: java網絡程式設計7、8、9習題解析 - 使用JDK類庫提供的線程池
java網絡程式設計5、6章習題解析第五章第六章下一節: java網絡程式設計7、8、9習題解析
第六章
-
預設情況下,SocketChannel對象處于什麼模式?(A)
A 阻塞模式
B 非阻塞模式
解析:配置非阻塞模式,
serverChannel. configureBlocking(false);
- 對于以下代碼:
int n=socketChannel.read(byteBuffer); //假定n>=0 byteBuffer.flip();
假定執行socketChannel.read(byteBuffer)方法前,byteBuffer的容量、極限和位置分别為c、l和p,執行完以上代碼後,byteBuffer的容量、極限和位置分别是多少?(B)
A 容量為c,極限為l,位置為p+n
B 容量為c,極限為p+n,位置為0
C 容量為l,極限為p+n,位置為0
D 容量為c,極限為p+n,位置為p+n
在Java NIO程式設計中,對緩沖區操作常常需要使用 java.nio.Buffer中的 flip()方法。
Buffer 中的 flip() 方法涉及到 Buffer 中的capacity、position、limit三個概念。
(1)capacity:在讀/寫模式下都是固定的,就是我們配置設定的緩沖大小(容量)。
(2)limit:在寫模式下表示最多能寫入多少資料,此時和capacity相同。在讀模式下表示最多能讀多少資料,此時和緩存中的實際資料大小相同。
(3)position:類似于讀/寫指針,表示目前讀(寫)到什麼位置。
flip():Buffer有兩種模式,寫模式和讀模式。在寫模式下調用flip()之後,Buffer從寫模式變成讀模式,那麼limit就設定成了position目前的值(即目前寫了多少資料),postion會被置為0,以表示讀操作從緩存的頭開始讀。也就是說調用flip()之後,讀/寫指針position指到緩沖區頭部,并且設定了最多隻能讀出之前寫入的資料長度(而不是整個緩存的容量大小)。
java網絡程式設計5、6章習題解析第五章第六章下一節: java網絡程式設計7、8、9習題解析 上三個屬性的關系為:容量>=極限>=位置>=0
擴充:
public final Buffer mark()和public final Buffer reset():用于标記位置将來回頭重讀或重寫
public final Buffer clear():“清空”緩沖區,把極限設為容量,再把位置設為0。
public final Buffer rewind():不改變極限,把位置設為0
public final Buffer flip():把極限設為位置,再把位置設為0。
public final int remaining():傳回Buffer的剩餘容量,取值等于極限-位置
public final boolean hasRemaining():Buffer是否還有剩餘容量
除了向Buffer裡寫資料的方法put()之外,Buffer的其它方法都不會改變Buffer中現有的值
-
在哪些情況,SelectionKey對象會失效?(ACD)
A 程式調用SelectionKey的cancel()方法。
B 程式調用SelectionKey的close()方法。
C 關閉與SelectionKey關聯的Channel。
D 與SelectionKey關聯的Selector被關閉。
在SelectionKey對象的有效期間,Selector會一直監控與SelectionKey對象相關的事件,如果事件發生,就會把SelectionKey對象加入到selected-keys集合中。
在以下情況,SelectionKey對象會失效,這意味着Selector再也不會監控與它相關的事件:
(1)程式調用SelectionKey的cancel()方法。
(2)關閉與SelectionKey關聯的Channel。
(3)與SelectionKey關聯的Selector被關閉。
-
SocketChannel可能發生哪些事件?(BCD)
A SelectionKey.OP_ACCEPT:接收連接配接就緒事件
B SelectionKey.OP_CONNECT:連接配接就緒事件。
C SelectionKey.OP_READ:讀就緒事件。
D SelectionKey.OP_WRITE:寫就緒事件。
SelectionKey類的一些靜态常量表示事件類型
(1)ServerSocketChannel隻可能發生一種事件:
SelectionKey.OP_ACCEPT:接收連接配接就緒事件
(2)SocketChannel可能發生以下三種事件:
SelectionKey.OP_CONNECT:連接配接就緒事件
SelectionKey.OP_READ:讀就緒事件
SelectionKey.OP_WRITE:寫就緒事件
-
在伺服器程式中,線程在哪些情況可能會進入阻塞狀态?(CDE)
A 線程執行Socket的getInputStream()方法獲得輸入流。
B 線程執行Socket的getOutputStream()方法獲得輸出流。
C 線程執行ServerSocket的accept()方法。
D 線程從Socket的輸入流讀入資料。
E 線程向Socket的輸出流寫一批資料。
用戶端線程進入阻塞的場景
(1)建立連接配接時
請求與伺服器建立連接配接時,會進入阻塞狀态,直到連接配接成功。
(2)讀資料時
從Socket的輸入流讀入資料時,如果沒有足夠的資料,就會進入阻塞狀态,直到讀到了足夠的資料(“足夠資料”對不同的read()方法有不同含義);或到達輸入流的末尾;或者出現了異常。
(3)寫資料時
線程向Socket的輸出流寫一批資料時,可能會進入阻塞狀态,直到寫出了所有的資料;或者出現異常。
(4)關閉Socket時
當調用Socket的setSoLinger()方法設定了關閉Socket的延遲時間,那麼當線程執行Socket的close()方法時,會進入阻塞狀态,直到底層Socket發送完所有剩餘資料;或者超過了setSoLinger()方法設定的延遲時間。
伺服器線程進入阻塞的場景
(1)線程執行ServerSocket的accept()方法,等待客戶的連接配接,直到接收到了客戶連接配接,才從accept()方法傳回。
(2)線程從Socket的輸入流讀入資料時, 如果輸入流沒有足夠的資料,就會進入阻塞狀态。
(3)線程向Socket的輸出流寫一批資料時,可能會進入阻塞狀态,等到輸出了所有的資料,或者出現異常,才從輸出流的write()方法傳回或異常中斷。
-
線程執行Selector對象的select(long timeout)方法時進入阻塞狀态,在哪些情況,線程會從select()方法中傳回?(ABDE)
A 至少有一個SelectionKey的相關事件已經發生。
B 其他線程調用了Selector對象的wakeup()方法。
C 與Selector對象關聯的一個SocketChannel對象被關閉。
D 目前執行select()方法的線程被其他線程中斷。
E 超出了等待時間。
public int select(long timeout)throws IOException
采用阻塞的工作方式,傳回相關事件已經發生的SelectionKey對象的數目,如果一個也沒有,就進入阻塞狀态,直到出現以下情況之一才傳回:
(1)至少一個SelctionKey對象的相關事件已經發生
(2)其它線程調用了這個Selector對象的wakeup()方法
(3)目前執行select()方法的線程被其它線程中斷
(4)超出了等待時間(不會抛出異常)
小結:
7. 非阻塞IO通道技術模型
8. 伺服器輪詢線程
3. Java支援Socket程式設計的類