socket通訊編程

這一塊屬于網(wǎng)絡(luò)編程,主要是學(xué)習(xí)TCP/IP四層的網(wǎng)絡(luò)體系結(jié)構(gòu),學(xué)習(xí)TCP編程和UDP編程。

java.net中


一.IP地址:

1.? IPV4:Inet4Address

IPV6 :Inet6Address

都繼承與InetAddress類,是java對IP地址的封裝,其實例對象包括ip地址和主機(jī)名。

2. InetAddress的構(gòu)造方法不是共有的,要通過static方法獲取實例對象:(獲取IP地址)

static InetAddress[] getAllByName(String host)

static InetAddress? getByAddress(byte[]? addr)?

static InetAddress getByAddress(String host,byte[]? addr)?

static InetAddress getByName(String host)? ?//傳入目標(biāo)主機(jī)的名字,如傳入網(wǎng)站網(wǎng)址

static InetAddress getLocalHost()? ?//返回本地ip地址

舉個栗子:

返回本地ip地址:

二、流

1.輸出流:基類是java.io.OutputStream? 抽象類(向流中寫數(shù)據(jù))

public abstract void write(int b) throws IOException;? //將指定字節(jié)寫入輸出流,只寫入低8位,高位拋棄

public void write(byte[] b) throws IOException;? //將byte數(shù)組所有字節(jié)寫入輸出流

(=write(b,0,b.length))

public void write(byte[] b,int off,int len) throws IOException;??//將byte數(shù)組指定字節(jié)寫入輸出流

public void flush() throws IOException //將輸出流緩存的所有字節(jié)寫向預(yù)期目標(biāo)

public void close() throws IOException? //關(guān)閉輸入流,釋放資源


2.輸入流:基類是java.io.InputStream? 抽象類(從輸入流讀取數(shù)據(jù))

public abstract int read() throws IOException? //從輸入流讀取數(shù)據(jù)下一個字節(jié),到達(dá)流末尾返回-1

public int read(byte[] b) throws IOException? //從輸入流讀取一定數(shù)量的字節(jié)

public int read(byte[] b,int off,int len) throws IOException? //從輸入流讀取一定數(shù)量的字節(jié)

public long skip(long n) throws??IOException? //跳過輸入流的n個字節(jié),并將這些字節(jié)丟棄

public int available()??throws IOException? //獲取輸入流中可供讀取或跳過的字節(jié)數(shù)

public void close()??throws IOException? //關(guān)閉輸入流,釋放資源


3.輸出流處理工具:java.io.Writer? (抽象類,向輸出流寫入...)

常用子類是PrinterWriter(有write()、print()、println() )

public void write(int c)??throws IOException;??

public void write(char[] cbuf)??throws IOException ;

public abstract void write(char[] cbuf,int off,int len)??throws IOException??

public void write(String s)??throws IOException??

public void write(String s,int off,int len)??throws IOException??


4.輸入流處理工具??java.io.Reader (抽象類)?

public int read()? throws IOException?

public int read(char[] cbuf)? throws IOException?

public abstract void read(char[] cbuf,int off,int len)??throws IOException??

public int read(CharBuffer target)? throws IOException?

常用子類有InputStreamReader、BufferedReader:(常配合使用)

通常使用:BufferedReader in =new?BufferedReader(new InputStreamReader(System.in))

即:InputStream? -->??InputStreamReader? -->??BufferedReader


5.套接字

流套接字:Socket? ServerSocket

數(shù)據(jù)報套接字: DatagramSocket? MulticastSocket


二、TCP編程(面向字節(jié)流,面向連接,可靠,面向連接,可以單播也可以廣播)

1.Socket(建立網(wǎng)絡(luò)連接時,兩端都產(chǎn)生一個socket實例,可操作這個實例完成會話)

構(gòu)造方法:

public Socket(String host,int port)? //指定主機(jī),指定端口

public Socket(InetAddress address, int port , InetAddress localAddr, int localPort)? //本地地址和端口,目的地的地址和端口

public Socket()

工具方法:(用于處理網(wǎng)絡(luò)會話)

public InputStream getInputStream()? throws IOException? //返回程序中套接字所能讀取的輸入流

public OutputStream getOutputStream()? throws IOException???//返回程序中套接字的輸出流

public void close()??throws IOException?

connect(SocketAddress endpoint)? //連接到遠(yuǎn)程服務(wù)器

getInetAddress()? //獲取遠(yuǎn)處服務(wù)器地址


2.ServerSocket(服務(wù)器端)

實現(xiàn)服務(wù)器套接字,等待請求通過網(wǎng)絡(luò)傳入,基于該請求執(zhí)行某些操作,然后可能向請求者返回結(jié)果。

數(shù)據(jù)報中傳輸?shù)臄?shù)據(jù)是以字節(jié)數(shù)組的形式存儲,所以當(dāng)定義了字符串之后,要轉(zhuǎn)換為字節(jié)數(shù)組? byte[]? buf=s.getBytes();

構(gòu)造方法:

?public ServerSocket()? throws IOException? //創(chuàng)造服務(wù)器套接字

?public ServerSocket(int port )? throws IOException? //指定監(jiān)聽端口(常用)

public ServerSocket(int port ,int backlog)? throws IOException //指定監(jiān)聽端口和接受的最大連接數(shù)

public ServerSocket(int port ,int backlog,InetAddress bindAddr)? throws IOException?//指定監(jiān)聽端口、地址和接受的最大連接數(shù)

工具方法:

public Socket accept()? throws IOException? ?//該方法一直處于阻塞狀態(tài),直到有新的連接接入,建立連接后,該方法會返回一個套接字,用于處理客戶端請求以及服務(wù)端響應(yīng)

public void setSoTimeout(int timeout) throws SocketException? //設(shè)置最大阻塞時間,超過就會拋出異常

public void close() throws IOException? //關(guān)閉服務(wù)器套接字


3.一對一通信

舉個栗子:客戶端向服務(wù)端發(fā)送連接請求,鏈接建立后,客戶端向服務(wù)端發(fā)送一個簡單的請求,服務(wù)端接收這個請求,根據(jù)請求內(nèi)容做相應(yīng)處理,并返回處理結(jié)果。

運行時,先運行服務(wù)器端。否則客戶端會因為無法創(chuàng)建連接而拋出異常。

關(guān)閉的時候一般先關(guān)閉工具,最后再關(guān)閉socket和 ServerSocket

server:要serversocket 和socket實例

server

Client:只要socket實例

Client

4.一對多通信

要實現(xiàn)一個服務(wù)器給多個客戶提供服務(wù),用多線程實現(xiàn)多客戶機(jī)制。服務(wù)器總是在指定端口監(jiān)聽是否有客戶請求,有則服務(wù)器啟動一個專門的服務(wù)線程來響應(yīng)該客戶的請求,而服務(wù)器在啟動完線程后又進(jìn)入監(jiān)聽狀態(tài),等待下一個客戶。

服務(wù)端定義兩個類,一個Server1負(fù)責(zé)監(jiān)聽連接和線程分配,一個SocketHandler負(fù)責(zé)套接字及流的處理??蛻舳瞬蛔儭?/p>

先執(zhí)行服務(wù)器類,再執(zhí)行客戶類。

Server1:監(jiān)聽連接和線程分配

SocketHandler:負(fù)責(zé)套接字及流的處理

運行結(jié)果:


三、UDP編程(面向報文,無連接,不可靠的,只能單播,不能單播)

1.DatagramPacket:(表示數(shù)據(jù)報包)

一個數(shù)據(jù)報文=一個DatagramPacket實例

發(fā)送信息,創(chuàng)建一個數(shù)據(jù)報文(一個DatagramPacket實例)將需要發(fā)送的信息封裝。

接受信息,創(chuàng)建一個數(shù)據(jù)報文(一個DatagramPacket實例),存儲接受的報文信息。

構(gòu)造方法:

用于接收的:

public DatagramPacket (byte[] buf,int length)? //接收長度為length的數(shù)據(jù)包

public DatagramPacket (byte[] buf, int offset, int length)//接收長度為length的數(shù)據(jù)包,在緩沖區(qū)中指定了偏移量

用于發(fā)送的:

public DatagramPacket (byte[] buf, int offset, int length,InetAddress address,int port):構(gòu)造數(shù)據(jù)報包,將長度為length 偏移量為offset的包發(fā)送到指定主機(jī)上的指定端口號

public DatagramPacket (byte[] buf,? int length,InetAddress address,int port):構(gòu)造數(shù)據(jù)報包,將長度為length 的包發(fā)送到指定主機(jī)上的指定端口號

public DatagramPacket (byte[] buf, int offset, int length, SocketAddress address)throws SocketException?構(gòu)造數(shù)據(jù)報包,將長度為length ?偏移量為offset的包發(fā)送到指定主機(jī)上的指定端口號

public DatagramPacket (byte[] buf, int length, SocketAddress address)throws SocketException?構(gòu)造數(shù)據(jù)報包,將長度為length 的包發(fā)送到指定主機(jī)上的指定端口號

設(shè)置地址和端口的方法:

public void setAddress(InetAddress iaddr)? //設(shè)置目標(biāo)主機(jī)IP地址

public void setPort(int iport)? //設(shè)置目標(biāo)程序的端口

public void setSocketAddress(SocketAddress address) //設(shè)置數(shù)據(jù)包的目的地(包括IP地址和端口號)

提供對數(shù)據(jù)處理的方法:

public void setData(byte[] buf)//設(shè)置長度為buf 的數(shù)據(jù)緩沖區(qū)

public void setData(byte[] buf,int offset, int length)//設(shè)置包的數(shù)據(jù)為buf,長度為length??偏移量為offset的數(shù)據(jù)緩沖區(qū)


2.DatagramSocket類:(表示數(shù)據(jù)包套接字,進(jìn)行端到端通信的類)

發(fā)送和接收UDP數(shù)據(jù)包= 接收和發(fā)送DatagramSocket對象

構(gòu)造方法:

public? DatagramSocket() throws SocketException //發(fā)送方使用

public?DatagramSocket(int port) throws SocketException //接收方使用,制定了監(jiān)聽的端口,只接受發(fā)往該端口的數(shù)據(jù)報。

public?DatagramSocket(int port,InetAddress address) throws SocketException //接收方使用,制定了監(jiān)聽的地址和端口,只接受發(fā)往該地址和端口的數(shù)據(jù)報。

public?DatagramSocket(SocketAddress bindaddr) throws SocketException //創(chuàng)建數(shù)據(jù)報套接字,指定了套接字地址,一般包含IP地址和端口

public?DatagramSocket(DatagramSocketImpl impl)///創(chuàng)建帶有指定DatagramSocketImpl數(shù)據(jù)報套接字

UDP發(fā)送和接受數(shù)據(jù)方法:

public? void send(?DatagramPacket p) throws IOException? //發(fā)送封裝好的數(shù)據(jù)報

public? void receive(?DatagramPacket p) throws IOException? //接收數(shù)據(jù)報,調(diào)用此方法后,將用接受的數(shù)據(jù)填充指定數(shù)據(jù)報對象。

用于限制UDP數(shù)據(jù)報發(fā)送方和接收方的方法:

public void connect(InetAddress address,int port) //連接指定IP地址和端口的目的地址,建立連接后,接收方只接受目的地址發(fā)送的數(shù)據(jù)報

public void connect(SocketAddress addr) throws SocketException? //連接指定套接字地址,建立連接后,接收方只接受目的地址發(fā)送的數(shù)據(jù)報

discount()? 用于斷開連接

舉個栗子:

客戶端封裝數(shù)據(jù)報,通過UDP套接字發(fā)送出去,服務(wù)端一直使用UDP套接字監(jiān)聽指定端口,當(dāng)監(jiān)聽到數(shù)據(jù)報時,接收并填充數(shù)據(jù)報對象,并返回確認(rèn)信息給客戶端,客戶端接收并填充數(shù)據(jù)報對象。

客戶端:(DatagramSocket數(shù)據(jù)報套接字只用創(chuàng)建一個,可用于發(fā)送和接收數(shù)據(jù)報;DatagramPacket數(shù)據(jù)報要創(chuàng)建一個用于封裝發(fā)送,一個用于填充接收到的服務(wù)端的確認(rèn)信息的數(shù)據(jù)報)

客戶端:(DatagramSocket數(shù)據(jù)報套接字只用創(chuàng)建一個,可用于發(fā)送和接收數(shù)據(jù)報;DatagramPacket數(shù)據(jù)報要創(chuàng)建一個用于接受數(shù)據(jù),一個用于封裝并發(fā)送確認(rèn)信息的數(shù)據(jù)報)

四、HTTP編程:

http傳輸模式:c/s模型,由客戶端發(fā)起請求,服務(wù)端回送響應(yīng)。

過程:1.建立http連接,該連接基于TCP可靠傳輸之上

2.建立連接后,客戶端向服務(wù)器發(fā)送http請求,(請求方式get、post等)

3.服務(wù)端接收請求后處理,將處理結(jié)果返回客戶端

4.應(yīng)答結(jié)束,關(guān)閉http連接(每次應(yīng)答都要!!因為每次的請求之間無關(guān))


舉個栗子:編寫簡單的應(yīng)用服務(wù)器,可為每個請求客戶端建立連接,接受并解析客戶端請求消息,處理用戶請求,將處理結(jié)果封裝成http響應(yīng)消息發(fā)送給客戶端。

server:

這里沒有貼客戶端的代碼,需要http請求消息格式。



總結(jié):

1

2、字符串轉(zhuǎn)字節(jié)數(shù)組:

byte[] buf=mes.getBytes();

字節(jié)數(shù)組轉(zhuǎn)字符串:

String backMes=new String(buf,0,getPacket.getLength());


3、從文件中讀取輸入流:

int read():讀取一個字節(jié),并返回讀取的字節(jié),無數(shù)據(jù)時返回-1

int read(byte[] b):讀取多個字節(jié),并存儲到數(shù)組b中,無數(shù)據(jù)時返回-1

int read(byte[] b,int off,int len):從數(shù)組b的索引off開始讀取len個字節(jié)

用file、inputstream

寫入文件:PrintWriter和FileWriter

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 一、基礎(chǔ)知識:1、JVM、JRE和JDK的區(qū)別:JVM(Java Virtual Machine):java虛擬機(jī)...
    殺小賊閱讀 2,565評論 0 4
  • 7.2 面向套接字編程我們已經(jīng)通過了解Socket的接口,知其所以然,下面我們就將通過具體的案例,來熟悉Socke...
    lucas777閱讀 1,276評論 0 2
  • 第二章 配羅那 今年是新元歷的第2018年,人類對煉獄星的探索已經(jīng)十分完善。 畸變種目前是這個星球最大的威脅,但并...
    小說隨寫閱讀 439評論 0 0
  • 《福爾摩斯探案集》是我的啟蒙小說,現(xiàn)在它仍然和之前提到的《哈利波特》并排擺在我書架最高的一層,不是因為他們鮮少翻動...
    王幼稚閱讀 840評論 9 3
  • 孩子,既然你這么愛玩游戲,甚至日后還想以此為業(yè),我們要約法三章。 1. 必須以健康為前提,玩一小時,必須暫停休息1...
    清茶也醉人_2b0e閱讀 242評論 0 0

友情鏈接更多精彩內(nèi)容