1.1、OIS參考模型
1.2、TCP/ip參考模型
1.3、網(wǎng)絡(luò)通訊要素
IP地址:IPV4/IPV6
端口號(hào):0-65535,一般0-1024,都被系統(tǒng)占用,MySQL:3306,Oracle:1521
傳輸協(xié)議:TCP/UDP
2.1、InetAddress 主機(jī)對(duì)象
IP 地址是 IP 使用的 32 位或 128 位無符號(hào)數(shù)字,它是一種低級(jí)協(xié)議,UDP 和 TCP 協(xié)議都是在它的基礎(chǔ)上構(gòu)建的
2.2、示例
import java.net.*;class IPDemo { public static void main(String[] args) throws Exception { //getLoaclHostAddress(); getAllByName(); } /* 獲取本機(jī)的IP和主機(jī)名 */ public static void getLoaclHostAddress() throws Exception { //返回本地主機(jī) InetAddress ia=InetAddress.getLocalHost(); System.out.PRintln(ia.toString()); //主機(jī)名 String hostName=ia.getHostName(); //IP地址 String ip=ia.getHostAddress(); System.out.println("hostName="+hostName+".....ip="+ip); } /* 獲取163或者百度的所有IP地址集合 */ public static void getAllByName() throws Exception { //獲取淘寶的主機(jī)數(shù)組 InetAddress [] ia=InetAddress.getAllByName("www.163.com"); for(InetAddress i:ia) { //輸出主機(jī)IP地址 System.out.println("IP:"+i.getHostAddress()); System.out.println("Name:"+i.getHostName()); } }}
3.1、概述
4.1、Socket
Socket就是為網(wǎng)絡(luò)服務(wù)提供的一種機(jī)制
通信兩端都有Socket
網(wǎng)絡(luò)通信其實(shí)就是Socket間的通信
數(shù)據(jù)在兩個(gè)Socket間通過IO通信
五、UDP
5.1、概述
此類表示用來發(fā)送和接收數(shù)據(jù)報(bào)包的套接字。
構(gòu)造方法摘要 | |
---|---|
DatagramSocket() 構(gòu)造數(shù)據(jù)報(bào)套接字并將其綁定到本地主機(jī)上任何可用的端口。 | |
protected | DatagramSocket(DatagramSocketImpl impl) 創(chuàng)建帶有指定 DatagramSocketImpl 的未綁定數(shù)據(jù)報(bào)套接字。 |
DatagramSocket(int port) 創(chuàng)建數(shù)據(jù)報(bào)套接字并將其綁定到本地主機(jī)上的指定端口。 | |
DatagramSocket(int port, InetAddress laddr) 創(chuàng)建數(shù)據(jù)報(bào)套接字,將其綁定到指定的本地地址。 | |
DatagramSocket(SocketAddress bindaddr) 創(chuàng)建數(shù)據(jù)報(bào)套接字,將其綁定到指定的本地套接字地址。 |
此類表示數(shù)據(jù)報(bào)包。
數(shù)據(jù)報(bào)包用來實(shí)現(xiàn)無連接包投遞服務(wù)。每條報(bào)文僅根據(jù)該包中包含的信息從一臺(tái)機(jī)器路由到另一臺(tái)機(jī)器。從一臺(tái)機(jī)器發(fā)送到另一臺(tái)機(jī)器的多個(gè)包可能選擇不同的路由,也可能按不同的順序到達(dá)。不對(duì)包投遞做出保證。
構(gòu)造方法摘要 | |
---|---|
DatagramPacket(byte[] buf, int length) 構(gòu)造 DatagramPacket ,用來接收長(zhǎng)度為 length 的數(shù)據(jù)包。 | |
DatagramPacket(byte[] buf, int length, InetAddress address, int port) 構(gòu)造數(shù)據(jù)報(bào)包,用來將長(zhǎng)度為 length 的包發(fā)送到指定主機(jī)上的指定端口號(hào)。 | |
DatagramPacket(byte[] buf, int offset, int length) 構(gòu)造 DatagramPacket ,用來接收長(zhǎng)度為 length 的包,在緩沖區(qū)中指定了偏移量。 | |
DatagramPacket(byte[] buf, int offset, int length, InetAddress address, int port) 構(gòu)造數(shù)據(jù)報(bào)包,用來將長(zhǎng)度為 length 偏移量為 offset 的包發(fā)送到指定主機(jī)上的指定端口號(hào)。 | |
DatagramPacket(byte[] buf, int offset, int length, SocketAddress address) 構(gòu)造數(shù)據(jù)報(bào)包,用來將長(zhǎng)度為 length 偏移量為 offset 的包發(fā)送到指定主機(jī)上的指定端口號(hào)。 | |
DatagramPacket(byte[] buf, int length, SocketAddress address) 構(gòu)造數(shù)據(jù)報(bào)包,用來將長(zhǎng)度為 length 的包發(fā)送到指定主機(jī)上的指定端口號(hào)。 |
5.2、UDP發(fā)送端
/*發(fā)送端1.創(chuàng)建UDP服務(wù),通過DatagramSocekt,2.創(chuàng)建發(fā)送的數(shù)據(jù),并封裝為數(shù)據(jù)包,DatagramPacket3.發(fā)送send4.關(guān)閉DatagramSocekt資源*/import java.net.*;class UdpSend { public static void main(String[] args) throws Exception { //1.創(chuàng)建UDP服務(wù),通過DatagramSocekt, DatagramSocket ds=new DatagramSocket(); //2.創(chuàng)建發(fā)送的數(shù)據(jù),并封裝為數(shù)據(jù)包,DatagramPacket String say="udp數(shù)據(jù)!"; byte [] buf = say.getBytes(); InetAddress ia=InetAddress.getByName("localhost"); int port =9898; DatagramPacket dp=new DatagramPacket(buf,buf.length,ia,port); //3.發(fā)送send ds.send(dp); //4.關(guān)閉DatagramSocekt資源 ds.close(); }}
5.3、UDP接收端服務(wù)端
/*接收端,服務(wù)端1.創(chuàng)建UDP,Socket服務(wù)對(duì)象,DatagramSocket,設(shè)置商品2.創(chuàng)建數(shù)據(jù)服包對(duì)象DatagramPacket包,接收數(shù)據(jù)報(bào)包3.接收receive,到數(shù)據(jù)包在4.通過數(shù)據(jù)報(bào)包,獲取其中的數(shù)據(jù)如IP,數(shù)據(jù)和端口5.解析數(shù)據(jù)轉(zhuǎn)化為字符串,并打印6.關(guān)閉資源*/import java.net.*;class UdpReceive { public static void main(String[] args) throws Exception { //1.創(chuàng)建UDP,Socket服務(wù)對(duì)象,DatagramSocket,設(shè)置端口 DatagramSocket ds=new DatagramSocket(9898); //2.創(chuàng)建數(shù)據(jù)服包對(duì)象DatagramPacket包,接收數(shù)據(jù)報(bào)包 //接收內(nèi)容的字節(jié)數(shù)據(jù) byte[] buf=new byte[1024]; DatagramPacket dp=new DatagramPacket(buf,buf.length); //3.接收receive,到數(shù)據(jù)包在 ds.receive(dp); //4.通過數(shù)據(jù)報(bào)包,獲取其中的數(shù)據(jù)如IP,數(shù)據(jù)和端口 //IPD String ip=dp.getAddress().getHostAddress(); //主機(jī)名 String hostname=dp.getAddress().getHostName(); //數(shù)據(jù) String data=new String(dp.getData(),0,dp.getLength()); //5.解析數(shù)據(jù)轉(zhuǎn)化為字符串,并打印 System.out.println(ip+":"+hostname+":"+data); //6.關(guān)閉資源 ds.close(); }}
5.4、鍵盤錄入
/*發(fā)送端鍵盤錄入*/import java.net.*;import java.io.*;class UdpSend2 { public static void main(String[] args) throws Exception { //建立UDPSocket服務(wù)對(duì)象DatagramSocket DatagramSocket ds=new DatagramSocket(); //主機(jī)對(duì)象 InetAddress ia=InetAddress.getByName("localhost"); int port=10001; //錄入數(shù)據(jù),字符流,鍵盤錄入 BufferedReader br=new BufferedReader(new InputStreamReader(System.in)); String line=null; while((line=br.readLine())!=null) { if("886".equals(line)) break; //封裝為數(shù)據(jù)報(bào)包 byte [] buf=line.getBytes(); DatagramPacket dp=new DatagramPacket(buf,buf.length,ia,port); //發(fā)送 ds.send(dp); } //關(guān)閉 br.close(); ds.close(); }}
/*接收端一直開啟*/import java.net.*;class UdpRece2 { public static void main(String[] args) throws Exception { //建立DatagramSocket對(duì)象服務(wù),并指定端口 DatagramSocket ds=new DatagramSocket(10001); while(true) { //接收數(shù)據(jù)報(bào)包 byte[] buf=new byte[1024]; DatagramPacket dp=new DatagramPacket(buf,buf.length); //接收 ds.receive(dp); //獲取數(shù)據(jù)報(bào)中的數(shù)據(jù) String ip=dp.getAddress().getHostAddress(); String data=new String(dp.getData(),0,dp.getLength()); System.out.println(ip+":"+data); } }}
5.5、示例
package com.pb.demo1;/*簡(jiǎn)單聊天工具*///發(fā)送端import java.net.*;import java.io.*;class Send implements Runnable{ private DatagramSocket ds; public Send( DatagramSocket ds) { this.ds=ds; } //線程重寫方法 public void run() { try {//接收鍵盤錄入 BufferedReader br=new BufferedReader(new InputStreamReader(System.in)); InetAddress ia=InetAddress.getByName("192.168.2.255"); int port =10002; String line=null; while ((line=br.readLine())!=null) { if("886".equals(line)) break; //封裝數(shù)據(jù) byte[] buf=line.getBytes(); DatagramPacket dp=new DatagramPacket(buf,buf.length,ia,port); //發(fā)送 ds.send(dp); } } catch (Exception e) { throw new RuntimeException("發(fā)送失敗!"); } } }//接收端class Rece implements Runnable{ private DatagramSocket ds; public Rece( DatagramSocket ds) { this.ds=ds; } //線程重寫方法 public void run() { try { while (true) { //接收 byte[] buf=new byte[1024]; DatagramPacket dp=new DatagramPacket(buf,buf.length); ds.receive(dp); //通過數(shù)據(jù)報(bào)獲取信息 String ip=dp.getAddress().getHostAddress(); String data=new String(dp.getData(),0,dp.getLength()); //輸出 System.out.println(ip+":"+data); } } catch (Exception e) { throw new RuntimeException("接收失敗!"); } } }class ChatDemo { public static void main(String[] args) throws Exception { //發(fā)送 DatagramSocket send=new DatagramSocket(); //接收 DatagramSocket rece=new DatagramSocket(10002); new Thread(new Send(send)).start(); new Thread(new Rece(rece)).start(); }}
5.1、概述
5.2、TCP傳輸一次-簡(jiǎn)單使用
/*TCP傳輸1.TCP分客戶端與服務(wù)端2.客戶端:Socket 服務(wù)端:ServerSocket*//*客戶端:Socket() 通過系統(tǒng)默認(rèn)類型的 SocketImpl 創(chuàng)建未連接套接字 Socket(InetAddress address, int port) 創(chuàng)建一個(gè)流套接字并將其連接到指定 IP 地址的指定端口號(hào)。 Socket(InetAddress host, int port, boolean stream) 已過時(shí)。 Use DatagramSocket instead for UDP transport. Socket(InetAddress address, int port, InetAddress localAddr, int localPort) 創(chuàng)建一個(gè)套接字并將其連接到指定遠(yuǎn)程地址上的指定遠(yuǎn)程端口。 Socket(Proxy proxy) 創(chuàng)建一個(gè)未連接的套接字并指定代理類型(如果有),該代理不管其他設(shè)置如何都應(yīng)被使用。 protected Socket(SocketImpl impl) 使用用戶指定的 SocketImpl 創(chuàng)建一個(gè)未連接 Socket。 Socket(String host, int port) 創(chuàng)建一個(gè)流套接字并將其連接到指定主機(jī)上的指定端口號(hào)。 Socket(String host, int port, boolean stream) 已過時(shí)。 使用 DatagramSocket 取代 UDP 傳輸。 Socket(String host, int port, InetAddress localAddr, int localPort) 創(chuàng)建一個(gè)套接字并將其連接到指定遠(yuǎn)程主機(jī)上的指定遠(yuǎn)程端口。 通過構(gòu)造方法可以發(fā)現(xiàn):Socket對(duì)象,在建立時(shí),就可以去連接指定主機(jī)因?yàn)門cp是面向連接的,所以在連接成功,形成通路后,在該通道進(jìn)行數(shù)據(jù)的傳輸步驟:1.創(chuàng)建客戶端Socket服務(wù),指定主機(jī)與端口2.獲取Socket流,socket.getXXX(InputStream或者OutputStream,并封裝為字符流或者字節(jié)流3.發(fā)送數(shù)據(jù)4.關(guān)閉socket服務(wù)*/import java.net.*;import java.io.*;class TcpClient{ public static void main(String[] args) throws Exception { //1.創(chuàng)建客戶端Socket服務(wù),指定主機(jī)與端口 Socket s=new Socket("localhost",10003); //2.獲取Socket流,socket.getXXX(InputStream或者OutputStream,并封裝為字符流或者字節(jié)流 OutputStream os=s.getOutputStream(); //3.發(fā)送數(shù)據(jù) String say="Tcp客戶端發(fā)送,測(cè)試數(shù)據(jù)!"; os.write(say.getBytes()); //4.關(guān)閉socket服務(wù) s.close(); }}/*步驟:1.創(chuàng)建服務(wù)端Socket服務(wù),指定端口2.監(jiān)聽accept,并獲取Socket流,沒有連接,這個(gè)方法是阻塞工的3.獲取對(duì)應(yīng)客戶端對(duì)象的socket.getXXX(InputStream或者OutputStream,并封裝為字符流或者字節(jié)流4.接收數(shù)據(jù)InptuStream或者發(fā)送OutputStream5.打印6.(可選一般不關(guān)閉)關(guān)閉socket服務(wù)*/class TcpServer{ public static void main(String[] args) throws Exception { //1.創(chuàng)建服務(wù)端Socket服務(wù),指定端口 ServerSocket ss=new ServerSocket(10003); //2.監(jiān)聽accept,并獲取Socket流,沒有連接,這個(gè)方法是阻塞工的 Socket s=ss.accept(); //3.獲取對(duì)應(yīng)客戶端對(duì)象的socket.getXXX(InputStream或者OutputStream,并封裝為字符流或者字節(jié)流 //4.接收數(shù)據(jù)InptuStream或者發(fā)送OutputStream InputStream is=s.getInputStream(); //獲取客戶端IP String ip=s.getInetAddress().getHostAddress(); //設(shè)置緩沖區(qū) byte[] buf=new byte[1024]; //把數(shù)據(jù)讀取到緩沖區(qū)中 int len=is.read(buf); //轉(zhuǎn)換為字符串 String data=new String(buf,0,len); //5.打印 System.out.println(ip+"........"); System.out.println(data); //6.(可選一般不關(guān)閉)關(guān)閉socket服務(wù) s.close(); ss.close(); }}
5.3、SocetKet接收與返回
/*客戶端給服務(wù)端發(fā)送數(shù)據(jù)服務(wù)端收到后給客戶端反饋信息客戶接收反饋數(shù)據(jù)*//*步驟:1.創(chuàng)建客戶端Socket服務(wù),指定主機(jī)與端口2.獲取Socket流,socket.getXXX(InputStream或者OutputStream,并封裝為字符流或者字節(jié)流3.發(fā)送數(shù)據(jù)4.關(guān)閉socket服務(wù)*/import java.net.*;import java.io.*;class TcpClient2 { public static void main(String[] args) throws Exception { //1.建立Socekt服務(wù)并指定端口 Socket s=new Socket("localhost",10004); //2.信息 String sendInfo="客戶端發(fā)送的信息!"; //3.獲取輸出流寫到服務(wù)端 OutputStream os=s.getOutputStream(); os.write(sendInfo.getBytes()); //4.獲取輸入信息接收服務(wù)端信息 InputStream is=s.getInputStream(); byte [] buf=new byte[1024]; int len=is.read(buf); String rev=new String(buf,0,len); System.out.println("服務(wù)端反饋的信息:"+rev); s.close(); }}/*步驟:1.創(chuàng)建服務(wù)端Socket服務(wù),指定端口2.監(jiān)聽accept,并獲取Socket流,沒有連接,這個(gè)方法是阻塞工的3.獲取對(duì)應(yīng)客戶端對(duì)象的socket.getXXX(InputStream或者OutputStream,并封裝為字符流或者字節(jié)流4.接收數(shù)據(jù)InptuStream或者發(fā)送OutputStream5.打印6.(可選一般不關(guān)閉)關(guān)閉socket服務(wù)*/class TcpServer2{ public static void main(String[] args) throws Exception { //建立服務(wù)端ServerSocket數(shù)據(jù) ServerSocket ss=new ServerSocket(10004); //獲取客戶端對(duì)象accept, Socket s=ss.accept(); //獲取輸入流對(duì)象接收客戶端信息 InputStream is=s.getInputStream(); //建立緩沖區(qū) byte [] buf=new byte[1024]; int len=is.read(buf); String clientInfo=new String(buf,0,len); //獲取IP String ip=s.getInetAddress().getHostAddress(); System.out.println(ip+"....."+clientInfo); //返回給客戶端的信息 String rel="已經(jīng)收到了"; //獲取輸出流對(duì)象 OutputStream os=s.getOutputStream(); os.write(rel.getBytes()); //關(guān)閉 可選 s.close(); ss.close(); }}
5.4、綜合
/*建立一個(gè)轉(zhuǎn)換服務(wù)器客戶端輸入內(nèi)容到服務(wù)器,服務(wù)把內(nèi)容轉(zhuǎn)成大寫再返回給客戶端客戶端可以 不斷的進(jìn)行文本輸入,當(dāng)客戶端輸入over時(shí)結(jié)束*//*客戶端操作設(shè)備上的數(shù)據(jù),可以使用IO技術(shù)并按照IO的操作規(guī)律來完成源:鍵盤錄入目的:網(wǎng)絡(luò)設(shè)置,網(wǎng)絡(luò)輸出而且操作的是文本數(shù)據(jù),可以選擇字符流與字符緩沖流*/import java.io.*;import java.net.*;class TcpClient3{ public static void main(String[] args) throws Exception { //建立服務(wù) Socket s=new Socket("localhost",10005); //獲取鍵盤錄入 BufferedReader br= new BufferedReader(new InputStreamReader(System.in)); //目的發(fā)送給服務(wù)端 //BufferedWriter bwOut=new BufferedWriter(new OutputStreamWriter(s.getOutputStream())); //打印流,可以接收字符流、緩沖流、字節(jié)流,第二個(gè)參數(shù)true表示自動(dòng)刷新 PrintWriter out=new PrintWriter(s.getOutputStream(),true); //獲取服務(wù)端返回的信息 BufferedReader brIn= new BufferedReader(new InputStreamReader(s.getInputStream())); //鍵盤錄入數(shù)據(jù) String line=null; //服務(wù)端返回?cái)?shù)據(jù) String recLine=null; //接收鍵盤錄入 while((line=br.readLine())!=null) { if("over".equals(line)) break; out.println(line); /* //將信息寫入服務(wù)端 bwOut.write(line); //增加換行 bwOut.newLine(); //刷新緩沖區(qū) bwOut.flush(); */ //獲取取服務(wù)端返回的大寫數(shù)據(jù) recLine=brIn.readLine(); System.out.println("服務(wù)器返回信息:"+recLine); } //結(jié)束,關(guān)資源 s.close(); }}/*服務(wù)器*/class TcpServer3{ public static void main(String[] args) throws Exception { //建立服務(wù)端對(duì)象 ServerSocket ss=new ServerSocket(10005); //獲取客戶端Socket對(duì)象 Socket s=ss.accept(); String ip=s.getInetAddress().getHostAddress(); System.out.println(ip+"...."); //獲取客戶端流對(duì)象 BufferedReader brIn= new BufferedReader(new InputStreamReader(s.getInputStream())); //BufferedWriter bwOut=new BufferedWriter(new OutputStreamWriter(s.getOutputStream())); //打印流,可以接收字符流也可以接收字節(jié)流,加true自動(dòng)刷新 PrintWriter out=new PrintWriter(s.getOutputStream(),true); String line=null; while((line=brIn.readLine())!=null) { System.out.println("客戶端說:"+line); out.println(line.toUpperCase()); /* //轉(zhuǎn)換為大寫返回客戶端 bwOut.write(line.toUpperCase()); //增加換行 bwOut.newLine(); //刷新緩沖區(qū) bwOut.flush(); */ } s.close(); ss.close(); }}/*問題:客戶端和服務(wù)端都在莫名的等待因?yàn)榭蛻舳撕头?wù)端都在阻塞的方法,這些方法沒有讀到結(jié)束標(biāo)記,那么就一直等待而導(dǎo)致兩端,都在等待*/
5.5、示例-TCP文件復(fù)制
/*上傳一個(gè)文件到服務(wù)器*/import java.net.*;import java.io.*;/*客戶端*/class UploadClient { public static void main(String[] args) throws Exception { //建立客戶端服務(wù) Socket s=new Socket("localhost",10009); //上傳文件 File file=new File("d://gm.mp3"); //獲取文件名 String filename=file.getName(); //建立基本數(shù)據(jù)流將文件名發(fā)送過去 PrintWriter pw=new PrintWriter(s.getOutputStream(),true); //發(fā)送 pw.println(filename); //建立輸入流 FileInputStream fis=new FileInputStream(file); BufferedInputStream bis=new BufferedInputStream(fis); //建立流輸出 BufferedOutputStream bos=new BufferedOutputStream(s.getOutputStream()); //建立字符緩沖,接收服務(wù)端返回的提示信息 BufferedReader br=new BufferedReader(new InputStreamReader(s.getInputStream())); int len=0; while((len=bis.read())!=-1) { bos.write(len); bos.flush(); } //關(guān)閉輸出流,增加結(jié)束標(biāo)記 s.shutdownOutput(); String str=br.readLine(); System.out.println(str); bis.close(); fis.close(); s.close(); }}/*服務(wù)端*/class UploadServer { public static void main(String[] args) throws Exception { //建立服務(wù) ServerSocket ss=new ServerSocket(10009); //獲取客戶端對(duì)象 Socket s=ss.accept(); //獲取客戶端 發(fā)送的文件名 BufferedReader br=new BufferedReader(new InputStreamReader(s.getInputStream())); String filename=br.readLine(); System.out.println("文件名:"+filename); //文件輸讀流 BufferedInputStream bis=new BufferedInputStream(s.getInputStream()); //文件輸出流 File f=new File("f://",filename); BufferedOutputStream bos=new BufferedOutputStream(new FileOutputStream(f)); //輸出提示信息 PrintWriter pw=new PrintWriter(s.getOutputStream(),true); int len=0; while((len=bis.read())!=-1) { bos.write(len); bos.flush(); } pw.println("上傳成功"); bos.close(); s.close(); ss.close(); }}
新聞熱點(diǎn)
疑難解答
圖片精選
網(wǎng)友關(guān)注