<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    Flying with the dream!

    與其慷慨罵邪惡,不如奮斗求善良!

    JAVA 網絡編程

    課前思考
      1. 什么是TCP/ IP協議?
      2. TCP/IP有哪兩種傳輸協議,各有什么特點?
      3. 什么是URL
      4. URLIP地址有什么樣的關系?
      5. 什么叫套接字(Socket)?
      6. 套接字(Socket)和TCP/IP協議的關系?
      7. URL和套接字(Socket)的關系?
    8.1 網絡編程基本概念,TCP/IP協議簡介

    8.1.1 網絡基礎知識

    網絡編程的目的就是指直接或間接地通過網絡協議與其他計算機進行通訊。網絡編程中有兩個主要的問題,一個是如何準確的定位網絡上一臺或多臺主機,另一個就是找到主機后如何可靠高效的進行數據傳輸。在TCP/IP協議中IP層主要負責網絡主機的定位,數據傳輸的路由,由IP地址可以唯一地確定Internet上的一臺主機。而TCP層則提供面向應用的可靠的或非可靠的數據傳輸機制,這是網絡編程的主要對象,一般不需要關心IP層是如何處理數據的。
      目前較為流行的網絡編程模型是客戶機/服務器(C/S)結構。即通信雙方一方作為服務器等待客戶提出請求并予以響應。客戶則在需要服務時向服務器提出申請。服務器一般作為守護進程始終運行,監聽網絡端口,一旦有客戶請求,就會啟動一個服務進程來響應該客戶,同時自己繼續監聽服務端口,使后來的客戶也能及時得到服務。

    8.1.3兩類傳輸協議:TCP;UDP
      盡管TCP/IP協議的名稱中只有TCP這個協議名,但是在TCP/IP的傳輸層同時存在TCPUDP兩個協議。

    TCPTranfer Control Protocol的簡稱,是一種面向連接的保證可靠傳輸的協議。通過TCP協議傳輸,得到的是一個順序的無差錯的數據流。發送方和接收方的成對的兩個socket之間必須建立連接,以便在TCP協議的基礎上進行通信,當一個socket(通常都是server socket)等待建立連接時,另一個socket可以要求進行連接,一旦這兩個socket連接起來,它們就可以進行雙向數據傳輸,雙方都可以進行發送或接收操作。
      UDPUser Datagram Protocol的簡稱,是一種無連接的協議,每個數據報都是一個獨立的信息,包括完整的源地址或目的地址,它在網絡上以任何可能的路徑傳往目的地,因此能否到達目的地,到達目的地的時間以及內容的正確性都是不能被保證的。
      下面我們對這兩種協議做簡單比較:
      使用UDP時,每個數據報中都給出了完整的地址信息,因此無需要建立發送方和接收方的連接。對于TCP協議,由于它是一個面向連接的協議,在socket之間進行數據傳輸之前必然要建立連接,所以在TCP中多了一個連接建立的時間。
     
     使用UDP傳輸數據時是有大小限制的,每個被傳輸的數據報必須限定在64KB之內。而TCP沒有這方面的限制,一旦連接建立起來,雙方的socket就可以按統一的格式傳輸大量的數據。UDP是一個不可靠的協議,發送方所發送的數據報并不一定以相同的次序到達接收方。而TCP是一個可靠的協議,它確保接收方完全正確地獲取發送方所發送的全部數據。
      總之,TCP在網絡通信上有極強的生命力,例如遠程連接(Telnet)和文件傳輸(FTP)都需要不定長度的數據被可靠地傳輸。相比之下UDP操作簡單,而且僅需要較少的監護,因此通常用于局域網高可靠性的分散系統中client/server應用程序。
      讀者可能要問,既然有了保證可靠傳輸的TCP協議,為什么還要非可靠傳輸的UDP協議呢?主要的原因有兩個。一是可靠的傳輸是要付出代價的,對數據內容正確性的檢驗必然占用計算機的處理時間和網絡的帶寬,因此TCP傳輸的效率不如UDP高。二是在許多應用中并不需要保證嚴格的傳輸可靠性,比如視頻會議系統,并不要求音頻視頻數據絕對的正確,只要保證連貫性就可以了,這種情況下顯然使用UDP會更合理一些。

    8.2 基于URL的高層次Java網絡編程

    8.2.1一致資源定位器URL

    URL(Uniform Resource Locator)是一致資源定位器的簡稱,它表示Internet上某一資源的地址。通過URL我們可以訪問Internet上的各種網絡資源,比如最常見的WWWFTP站點。瀏覽器通過解析給定的URL可以在網絡上查找相應的文件或其他資源。

    8.2.2 URL的組成

    protocol://resourceName
      協議名(protocol)指明獲取資源所使用的傳輸協議,如httpftpgopherfile等,資源名(resourceName)則應該是資源的完整地址,包括主機名、端口號、文件名或文件內部的一個引用。例如:
      http://www.sun.com/ 協議名://主機名
      http://home.netscape.com/home/welcome.html 協議名://機器名+文件名
      http://www.gamelan.com:80/Gamelan/network.html#BOTTOM 協議名://機器名+端口號+文件名+內部引用.

    8.2.3 創建一個URL

    為了表示URL, java.net中實現了類URL。我們可以通過下面的構造方法來初始化一個URL對象:
      (1) public URL (String spec);
         通過一個表示URL地址的字符串可以構造一個URL對象。
         URL urlBase=new URL("http://www. 263.net/")
      (2) public URL(URL context, String spec);
         通過基URL和相對URL構造一個URL對象。
         URL net263=new URL ("http://www.263.net/");
         URL index263=new URL(net263, "index.html")
      (3) public URL(String protocol, String host, String file);
         new URL("http", "www.gamelan.com", "/pages/Gamelan.net. html");
      (4) public URL(String protocol, String host, int port, String file);
         URL gamelan=new URL("http", "www.gamelan.com", 80, "Pages/Gamelan.network.html");

      注意:類URL的構造方法都聲明拋棄非運行時例外(MalformedURLException),因此生成URL對象時,我們必須要對這一例外進行處理,通常是用try-catch語句進行捕獲。格式如下:

    try{
         URL myURL= new URL(…)
      }catch (MalformedURLException e){
        }

    8.2.4 解析一個URL

    一個URL對象生成后,其屬性是不能被改變的,但是我們可以通過類URL所提供的方法來獲取這些屬性:
       public String getProtocol() 獲取該URL的協議名。
       public String getHost() 獲取該URL的主機名。
       public int getPort() 獲取該URL的端口號,如果沒有設置端口,返回-1。
       public String getFile() 獲取該URL的文件名。
       public String getRef() 獲取該URL在文件中的相對位置。
       public String getQuery() 獲取該URL的查詢信息。
       public String getPath() 獲取該URL的路徑
       public String getAuthority() 獲取該URL的權限信息
       public String getUserInfo() 獲得使用者的信息
        public String getRef() 獲得該URL的錨

    8.2.5 從URL讀取WWW網絡資源

    當我們得到一個URL對象后,就可以通過它讀取指定的WWW資源。這時我們將使用URL的方法openStream(),其定義為:
             InputStream openStream();
      
      方法openSteam()與指定的URL建立連接并返回InputStream類的對象以從這一連接中讀取數據。
      public class URLReader {
      public static void main(String[] args) throws Exception {
                          //聲明拋出所有例外
        URL tirc = new URL("http://www.tirc1.cs.tsinghua.edu.cn/");
                          //構建一URL對象
        BufferedReader in = new BufferedReader(new InputStreamReader(tirc.openStream()));
        //使用openStream得到一輸入流并由此構造一個BufferedReader對象
        String inputLine;
        while ((inputLine = in.readLine()) != null)
                     //從輸入流不斷的讀數據,直到讀完為止
           System.out.println(inputLine); //把讀入的數據打印到屏幕上
        in.close(); //關閉輸入流
      }
      }

    8.2.6 通過URLConnetction連接WWW

    通過URL的方法openStream(),我們只能從網絡上讀取數據,如果我們同時還想輸出數據,例如向服務器端的CGI程序發送一些數據,我們必須先與URL建立連接,然后才能對其進行讀寫,這時就要用到類URLConnection了。CGI是公共網關接口(Common Gateway Interface)的簡稱,它是用戶瀏覽器和服務器端的應用程序進行連接的接口,有關CGI程序設計,請讀者參考有關書籍。
      URLConnection也在包java.net中定義,它表示Java程序和URL在網絡上的通信連接。當與一個URL建立連接時,首先要在一個URL對象上通過方法openConnection()生成對應的URLConnection對象。例如下面的程序段首先生成一個指向地址http://edu.chinaren.com/index.shtml的對象,然后用openConnection()打開該URL對象上的一個連接,返回一個URLConnection對象。如果連接過程失敗,將產生IOException.
      Try{
        URL netchinaren = new URL ("http://edu.chinaren.com/index.shtml");
        URLConnectonn tc = netchinaren.openConnection();
      }catch(MalformedURLException e){ //創建URL()對象失敗
      
      }catch (IOException e){ //openConnection()失敗
      
      }
      類URLConnection提供了很多方法來設置或獲取連接參數,程序設計時最常使用的是getInputStream()getOurputStream(),其定義為:
         InputSteram getInputSteram();
         OutputSteram getOutputStream();
      通過返回的輸入/輸出流我們可以與遠程對象進行通信。看下面的例子:
      URL url =new URL ("http://www.javasoft.com/cgi-bin/backwards");
      //創建一URL對象
      URLConnectin con=url.openConnection();
      //URL對象獲取URLConnection對象
      DataInputStream dis=new DataInputStream (con.getInputSteam());
      //URLConnection獲取輸入流,并構造DataInputStream對象
      PrintStream ps=new PrintSteam(con.getOutupSteam());
      //URLConnection獲取輸出流,并構造PrintStream對象
      String line=dis.readLine(); //從服務器讀入一行
      ps.println("client…"); //向服務器寫出字符串 "client…"
        其中backwards為服務器端的CGI程序。實際上,類URL的方法openSteam()是通過URLConnection來實現的。它等價于
        openConnection().getInputStream();
      基于URL的網絡編程在底層其實還是基于下面要講的Socket接口的。WWWFTP等標準化的網絡服務都是基于TCP協議的,所以本質上講URL編程也是基于TCP的一種應用.

    8.3 基于Socket的低層次Java網絡編程

    8.3.1 Socket通訊

    網絡上的兩個程序通過一個雙向的通訊連接實現數據的交換,這個雙向鏈路的一端稱為一個SocketSocket通常用來實現客戶方和服務方的連接。SocketTCP/IP協議的一個十分流行的編程界面,一個Socket由一個IP地址和一個端口號唯一確定。
      在傳統的UNIX環境下可以操作TCP/IP協議的接口不止Socket一個,Socket所支持的協議種類也不光TCP/IP一種,因此兩者之間是沒有必然聯系的。在Java環境下,Socket編程主要是指基于TCP/IP協議的網絡編程。

    8.3.2 Socket通訊的一般過程

    使用Socket進行Client/Server程序設計的一般連接過程是這樣的:ServerListen(監聽)某個端口是否有連接請求,Client端向Server端發出Connect(連接)請求,Server端向Client端發回Accept(接受)消息。一個連接就建立起來了。Server端和Client端都可以通過SendWrite等方法與對方通信。

    對于一個功能齊全的Socket,都要包含以下基本結構,其工作過程包含以下四個基本的步驟:
      (1創建Socket
      (2打開連接到Socket的輸入/出流;
      (3按照一定的協議對Socket進行讀/寫操作;
      (4關閉Socket.

    8.3.3 創建Socket

    java在包java.net中提供了兩個類SocketServerSocket,分別用來表示雙向連接的客戶端和服務端。這是兩個封裝得非常好的類,使用很方便。其構造方法如下:
      Socket(InetAddress address, int port);
      Socket(InetAddress address, int port, boolean stream);
      Socket(String host, int prot);
      Socket(String host, int prot, boolean stream);
      Socket(SocketImpl impl)
      Socket(String host, int port, InetAddress localAddr, int localPort)
      Socket(InetAddress address, int port, InetAddress localAddr, int localPort)
      ServerSocket(int port);
      ServerSocket(int port, int backlog);
      ServerSocket(int port, int backlog, InetAddress bindAddr)
      其中addresshostport分別是雙向連接中另一方的IP地址、主機名和端口號,stream指明socket是流socket還是數據報socketlocalPort表示本地主機的端口號,localAddrbindAddr是本地機器的地址(ServerSocket的主機地址),implsocket的父類,既可以用來創建serverSocket又可以用來創建Socketcount則表示服務端所能支持的最大連接數。例如:
      Socket client = new Socket("127.0.01.", 80);
      ServerSocket server = new ServerSocket(80);
      注意,在選擇端口時,必須小心。每一個端口提供一種特定的服務,只有給出正確的端口,才能獲得相應的服務。0~1023的端口號為系統所保留,例如http服務的端口號為80,telnet服務的端口號為21,ftp服務的端口號為23, 所以我們在選擇端口號時,最好選擇一個大于1023的數以防止發生沖突。
      在創建socket時如果發生錯誤,將產生IOException,在程序中必須對之作出處理。所以在創建SocketServerSocket是必須捕獲或拋出例外。

    8.3.8 簡單的Client/Server程序設計

    下面我們給出一個用Socket實現的客戶和服務器交互的典型的C/S結構的演示程序,讀者通過仔細閱讀該程序,會對前面所討論的各個概念有更深刻的認識。程序的意義請參考注釋。

    1. 客戶端程序
      import java.io.*;
      import java.net.*;
      public class TalkClient {
        public static void main(String args[]) {
          try{
            Socket socket=new Socket("127.0.0.1",4700);
            
    //向本機的4700端口發出客戶請求
            BufferedReader sin=new BufferedReader(new InputStreamReader(System.in));
            
    //由系統標準輸入設備構造BufferedReader對象
            PrintWriter os=new PrintWriter(socket.getOutputStream());
            
    //由Socket對象得到輸出流,并構造PrintWriter對象
            BufferedReader is=new BufferedReader(new InputStreamReader(socket.getInputStream()));
            
    //由Socket對象得到輸入流,并構造相應的BufferedReader對象
            String readline;
            readline=sin.readLine();
    //從系統標準輸入讀入一字符串
            while(!readline.equals("bye")){
            
    //若從標準輸入讀入的字符串為 "bye"則停止循環
              os.println(readline);
              
    //將從系統標準輸入讀入的字符串輸出到Server
              os.flush();
              
    //刷新輸出流,使Server馬上收到該字符串
              System.out.println("Client:"+readline);
              //在系統標準輸出上打印讀入的字符串

              System.out.println("Server:"+is.readLine());
              
    //從Server讀入一字符串,并打印到標準輸出上
              readline=sin.readLine(); //從系統標準輸入讀入一字符串
            } //繼續循環
            os.close(); //關閉Socket輸出流
            is.close(); //關閉Socket輸入流
            socket.close(); //關閉Socket
          }catch(Exception e) {
            System.out.println("Error"+e);
    //出錯,則打印出錯信息
          }
      }
    }

     2. 服務器端程序
      import java.io.*;
      import java.net.*;
      import java.applet.Applet;
      public class TalkServer{
        public static void main(String args[]) {
          try{
            ServerSocket server=null;
            try{
              server=new ServerSocket(4700);
            
    //創建一個ServerSocket在端口4700監聽客戶請求
            }catch(Exception e) {
              System.out.println("can not listen to:"+e);
            
    //出錯,打印出錯信息
            }

            Socket socket=null;
            try{
              socket=server.accept();
              
    //使用accept()阻塞等待客戶請求,有客戶
              //請求到來則產生一個Socket對象,并繼續執行

            }catch(Exception e) {
              System.out.println("Error."+e);
              
    //出錯,打印出錯信息
            }
            String line;
            BufferedReader is=new BufferedReader(new InputStreamReader(socket.getInputStream()));
             
    //由Socket對象得到輸入流,并構造相應的BufferedReader對象
            PrintWriter os=newPrintWriter(socket.getOutputStream());
             
    //由Socket對象得到輸出流,并構造PrintWriter對象
            BufferedReader sin=new BufferedReader(new InputStreamReader(System.in));
             
    //由系統標準輸入設備構造BufferedReader對象

            System.out.println("Client:"+is.readLine());
            
    //在標準輸出上打印從客戶端讀入的字符串
            line=sin.readLine();
            
    //從標準輸入讀入一字符串
            while(!line.equals("bye")){
            
    //如果該字符串為 "bye",則停止循環
              os.println(line);
              
    //向客戶端輸出該字符串
              os.flush();
              
    //刷新輸出流,使Client馬上收到該字符串
              System.out.println("Server:"+line);
              
    //在系統標準輸出上打印讀入的字符串
              System.out.println("Client:"+is.readLine());
              
    //從Client讀入一字符串,并打印到標準輸出上
              line=sin.readLine();
              
    //從系統標準輸入讀入一字符串
            }  
    //繼續循環
            os.close();
    //關閉Socket輸出流
            is.close();
    //關閉Socket輸入流
            socket.close();
    //關閉Socket
            server.close();
    //關閉ServerSocket
          }catch(Exception e){
            System.out.println("Error:"+e);
            
    //出錯,打印出錯信息
          }
        }
      }

    8.3.9 支持多客戶的client/server程序設計

    前面提供的Client/Server程序只能實現Server和一個客戶的對話。在實際應用中,往往是在服務器上運行一個永久的程序,它可以接收來自其他多個客戶端的請求,提供相應的服務。為了實現在服務器方給多個客戶提供服務的功能,需要對上面的程序進行改造,利用多線程實現多客戶機制。服務器總是在指定的端口上監聽是否有客戶請求,一旦監聽到客戶請求,服務器就會啟動一個專門的服務線程來響應該客戶的請求,而服務器本身在啟動完線程之后馬上又進入監聽狀態,等待下一個客戶的到來。

    ServerSocket serverSocket=null;
        boolean listening=true;
        try{
          serverSocket=new ServerSocket(4700);
          //創建一個ServerSocket在端口4700監聽客戶請求
        }catch(IOException e) {  }
        while(listening){ //永遠循環監聽
          new ServerThread(serverSocket.accept(),clientnum).start();
          //監聽到客戶請求,根據得到的Socket對象和
           客戶計數創建服務線程,并啟動之
          clientnum++; //增加客戶計數
        }
        serverSocket.close(); //關閉ServerSocket

    設計ServerThread

     public class ServerThread extends Thread{
       Socket socket=null; //保存與本線程相關的Socket對象
       int clientnum; //保存本進程的客戶計數
       public ServerThread(Socket socket,int num) { //構造函數
        this.socket=socket; //初始化socket變量
        clientnum=num+1; //初始化clientnum變量
       }
       public void run() { //線程主體
        try{//在這里實現數據的接受和發送}

    8.3.10 據報Datagram通訊

    前面在介紹TCP/IP協議的時候,我們已經提到,在TCP/IP協議的傳輸層除了TCP協議之外還有一個UDP協議,相比而言UDP的應用不如TCP廣泛,幾個標準的應用層協議HTTPFTPSMTP…使用的都是TCP協議。但是,隨著計算機網絡的發展,UDP協議正越來越來顯示出其威力,尤其是在需要很強的實時交互性的場合,如網絡游戲,視頻會議等,UDP更是顯示出極強的威力,下面我們就介紹一下Java環境下如何實現UDP網絡傳輸。

    8.3.11 什么是Datagram

    所謂數據報(Datagram)就跟日常生活中的郵件系統一樣,是不能保證可靠的寄到的,而面向鏈接的TCP就好比電話,雙方能肯定對方接受到了信息。在本章前面,我們已經對UDPTCP進行了比較,在這里再稍作小節:
      TCP,可靠,傳輸大小無限制,但是需要連接建立時間,差錯控制開銷大。
      UDP,不可靠,差錯控制開銷較小,傳輸大小限制在64K以下,不需要建立連接。

    8.3.12 Datagram通訊的表示方法:DatagramSocketDatagramPacket

    java.net中提供了兩個類DatagramSocketDatagramPacket用來支持數據報通信,DatagramSocket用于在程序之間建立傳送數據報的通信連接, DatagramPacket則用來表示一個數據報。先來看一下DatagramSocket的構造方法:
       DatagramSocket();
       DatagramSocketint prot;
       DatagramSocket(int port, InetAddress laddr)
        其中,port指明socket所使用的端口號,如果未指明端口號,則把socket連接到本地主機上一個可用的端口。laddr指明一個可用的本地地址。給出端口號時要保證不發生端口沖突,否則會生成SocketException類例外。注意:上述的兩個構造方法都聲明拋棄非運行時例外SocketException,程序中必須進行處理,或者捕獲、或者聲明拋棄。
      
    用數據報方式編寫client/server程序時,無論在客戶方還是服務方,首先都要建立一個DatagramSocket對象,用來接收或發送數據報,然后使用DatagramPacket類對象作為傳輸數據的載體。下面看一下DatagramPacket的構造方法
       DatagramPacketbyte buf[],int length);
       DatagramPacket(byte buf[], int length, InetAddress addr, int port);
       DatagramPacket(byte[] buf, int offset, int length)
       DatagramPacket(byte[] buf, int offset, int length, InetAddress address, int port)

      其中,buf中存放數據報數據,length為數據報中數據的長度,addrport旨明目的地址,offset指明了數據報的位移量。
      在接收數據前,應該采用上面的第一種方法生成一個DatagramPacket對象,給出接收數據的緩沖區及其長度。然后調用DatagramSocket 的方法receive()等待數據報的到來,receive()將一直等待,直到收到一個數據報為止。
      DatagramPacket packet=new DatagramPacket(buf, 256);
      Socket.receive (packet);
      發送數據前,也要先生成一個新的DatagramPacket對象,這時要使用上面的第二種構造方法,在給出存放發送數據的緩沖區的同時,還要給出完整的目的地址,包括IP地址和端口號。發送數據是通過DatagramSocket的方法send()實現的,send()根據數據報的目的地址來尋徑,以傳遞數據報。
      DatagramPacket packet=new DatagramPacket(buf, length, address, port);
      Socket.send(packet)
       
    在構造數據報時,要給出InetAddress類參數。類InetAddress在包java.net中定義,用來表示一個Internet地址,我們可以通過它提供的類方法getByName()從一個表示主機名的字符串獲取該主機的IP地址,然后再獲取相應的地址信息。

    8.3.14 用數據報進行廣播通訊

    DatagramSocket只允許數據報發送一個目的地址,java.net包中提供了一個類MulticastSocket,允許數據報以廣播方式發送到該端口的所有客戶。MulticastSocket用在客戶端,監聽服務器廣播來的數據。

    1. 客戶方程序:MulticastClient.java
      import java.io.*;
      import java.net.*;
      import java.util.*;
      public class MulticastClient {
        public static void main(String args[]) throws IOException
        {
         MulticastSocket socket=new MulticastSocket(4446);
         
    //創建4446端口的廣播套接字
         InetAddress address=InetAddress.getByName("230.0.0.1");
         
    //得到230.0.0.1的地址信息
         socket.joinGroup(address);
         
    //使用joinGroup()將廣播套接字綁定到地址上
         DatagramPacket packet;

         for(int i=0;i<5;i++) {
           byte[] buf=new byte[256];
           //創建緩沖區

           packet=new DatagramPacket(buf,buf.length);
           
    //創建接收數據報
           socket.receive(packet); //接收
           String received=new String(packet.getData());
           
    //由接收到的數據報得到字節數組,
           //并由此構造一個String對象
           System.out.println("Quote of theMoment:"+received);
           
    //打印得到的字符串
         } //循環5次
         socket.leaveGroup(address);
         
    //把廣播套接字從地址上解除綁定
         socket.close(); //關閉廣播套接字
       }
     }

     2. 服務器方程序:MulticastServer.java
      public class MulticastServer{
        public static void main(String args[]) throws java.io.IOException
        {
          new MulticastServerThread().start();
          
    //啟動一個服務器線程
        }
      }

     3. 程序MulticastServerThread.java
      import java.io.*;
      import java.net.*;
      import java.util.*;
      public class MulticastServerThread extends QuoteServerThread
      
    //從QuoteServerThread繼承得到新的服務器線程類MulticastServerThread
      {
        Private long FIVE_SECOND=5000;
    //定義常量,5秒鐘
        public MulticastServerThread(String name) throws IOException
        {
          super("MulticastServerThread");
          
    //調用父類,也就是QuoteServerThread的構造函數
        }

        public void run() //重寫父類的線程主體
        {
         while(moreQuotes) {
         
    //根據標志變量判斷是否繼續循環
          try{
            byte[] buf=new byte[256];
            
    //創建緩沖區
            String dString=null;
            if(in==null) dString=new Date().toString();
            
    //如果初始化的時候打開文件失敗了,
            //則使用日期作為要傳送的字符串

            else dString=getNextQuote();
            
    //否則調用成員函數從文件中讀出字符串
            buf=dString.getByte();
            
    //把String轉換成字節數組,以便傳送send it
            InetAddress group=InetAddress.getByName("230.0.0.1");
            
    //得到230.0.0.1的地址信息
            DatagramPacket packet=new DatagramPacket(buf,buf.length,group,4446);
            
    //根據緩沖區,廣播地址,和端口號創建DatagramPacket對象
            socket.send(packet); //發送該Packet
            try{
              sleep((long)(Math.random()*FIVE_SECONDS));
              
    //隨機等待一段時間,0~5秒之間
            }catch(InterruptedException e) { } //異常處理
          }catch(IOException e){ //異常處理
            e.printStackTrace( ); //打印錯誤棧

            moreQuotes=false; //置結束循環標志
          }
        }
        socket.close( );
    //關閉廣播套接口
       }
     }

    【本講小結】

    本講主要講解了Java環境下的網絡編程。因為TCP/IP協議是Java網絡編程的基礎知識,本講開篇重點介紹了TCP/IP協議中的一些概念,TCP/IP協議本身是一個十分龐大的系統,用幾個小節是不可能講清楚的。所以我們只是聯系實際,講解了一些最基本的概念,幫助學生理解后面的相關內容。重點有一下幾個概念:主機名,IP,端口,服務類型,TCPUDP
      后續的內容分為兩大塊,一塊是以URL為主線,講解如何通過URL類和URLConnection類訪問WWW網絡資源,由于使用URL十分方便直觀,盡管功能不是很強,還是值得推薦的一種網絡編程方法,尤其是對于初學者特別容易接受。本質上講,URL網絡編程在傳輸層使用的還是TCP協議。
      另一塊是以Socket接口和C/S網絡編程模型為主線,依次講解了如何用Java實現基于TCPC/S結構,主要用到的類有SocketServerSocket。以及如何用Java實現基于UDPC/S結構,還討論了一種特殊的傳輸方式,廣播方式,這種方式是UDP所特有的,主要用到的類有DatagramSocket , DatagramPacket, MulticastSocket。這一塊在Java網絡編程中相對而言是最難的(盡管Java在網絡編程這方面已經做的夠"傻瓜"了,但是網絡編程在其他環境下的卻是一件極為頭痛的事情,再"傻瓜"還是有一定的難度),也是功能最為強大的一部分,讀者應該好好研究,領悟其中的思想。
      最后要強調的是要學好Java網絡編程,Java語言,最重要的還是在于多多練習

    posted on 2008-09-13 21:53 老張 閱讀(203) 評論(0)  編輯  收藏


    只有注冊用戶登錄后才能發表評論。


    網站導航:
     
    主站蜘蛛池模板: 亚洲成A人片在线观看无码不卡 | 特级毛片免费观看视频| 亚洲最大AV网站在线观看| 人妻无码一区二区三区免费| 亚洲AV成人影视在线观看| 亚洲国产一成久久精品国产成人综合| 免费视频精品一区二区三区| 亚洲一线产区二线产区区| 中文字幕人成人乱码亚洲电影| 久久福利资源网站免费看| 美女羞羞喷液视频免费| 337p日本欧洲亚洲大胆色噜噜| 国产又长又粗又爽免费视频| 无码成A毛片免费| 一级一级一片免费高清| 亚洲综合中文字幕无线码| 亚洲乱色熟女一区二区三区丝袜| 成人av免费电影| 日韩内射激情视频在线播放免费| 国产精品自拍亚洲| 亚洲一线产区二线产区精华| 亚洲永久精品ww47| 四虎影院永久免费观看| 青娱乐免费在线视频| 先锋影音资源片午夜在线观看视频免费播放 | 国产又粗又猛又爽又黄的免费视频| 久久国产精品萌白酱免费| 无码人妻一区二区三区免费视频| 亚洲AV无码专区在线亚| 亚洲AV无码乱码在线观看裸奔| 亚洲国产成人乱码精品女人久久久不卡| 99在线精品免费视频九九视| 免费人成毛片动漫在线播放| 免费无码一区二区| 亚洲精品GV天堂无码男同| 亚洲精品在线视频观看| 亚洲AV福利天堂一区二区三| 亚洲日本一区二区三区在线| 亚洲精品国产V片在线观看| 国产成人涩涩涩视频在线观看免费 | 最好看的中文字幕2019免费|