W3Cschool
恭喜您成為首批注冊(cè)用戶
獲得88經(jīng)驗(yàn)值獎(jiǎng)勵(lì)
1.什么是計(jì)算機(jī)網(wǎng)絡(luò)
計(jì)算機(jī)網(wǎng)絡(luò),是指將地理位置不同的具有獨(dú)立功能的多臺(tái)計(jì)算機(jī)及其外部設(shè)備,通過(guò)通信線路連接起來(lái),在網(wǎng)絡(luò)操作系統(tǒng),網(wǎng)絡(luò)管理軟件及網(wǎng)絡(luò)通訊協(xié)議的管理和協(xié)調(diào)下,實(shí)現(xiàn)資源共享和信息傳遞的計(jì)算機(jī)系統(tǒng)
把分布在不同地理區(qū)域的計(jì)算機(jī)與專門的外部設(shè)備用通訊線路互連成一個(gè)規(guī)模大
功能強(qiáng)的網(wǎng)絡(luò)系統(tǒng),從而使眾多的計(jì)算機(jī)可以方便地相互傳遞信息,共享硬件,軟件、數(shù)據(jù)信息等資源
2.計(jì)算機(jī)網(wǎng)絡(luò)的主要功能
資源共享,信息傳輸與集中處理,均衡負(fù)荷與分布處理,綜合信息服務(wù)(www/綜合業(yè)務(wù)數(shù)字網(wǎng)絡(luò)ISDN)等
3.網(wǎng)絡(luò)通訊協(xié)議
要使計(jì)算機(jī)連成網(wǎng)絡(luò)能夠互相通信,需要對(duì)數(shù)據(jù)傳輸速率,傳輸代碼,代碼結(jié)構(gòu),傳輸控制步驟,出錯(cuò)
控制等制定一組標(biāo)準(zhǔn),這一組共同遵守的通訊標(biāo)準(zhǔn)就是網(wǎng)絡(luò)通訊協(xié)議
4.網(wǎng)絡(luò)通訊接口
為了是這兩個(gè)結(jié)點(diǎn)之間進(jìn)行對(duì)話,必須在它們之間建立通訊工具(既接口)
使彼此之間能進(jìn)行信息交換,接口包括兩部分:
1.硬件裝置:實(shí)現(xiàn)結(jié)點(diǎn)之間的信息傳遞
2.軟件裝置:規(guī)定雙方進(jìn)行通訊的約定協(xié)議
4.TCP/IP
5.程序開(kāi)發(fā)結(jié)構(gòu)
5.IP協(xié)議
IP協(xié)議是Internet上使用的一個(gè)關(guān)鍵協(xié)議,它的全稱是Internet Protocol,即Internet協(xié)議,通常簡(jiǎn)稱IP協(xié)議
通過(guò)使用IP協(xié)議,從而使Internet成為一個(gè)允許連接不同類型的計(jì)算機(jī)和不同操作系統(tǒng)的網(wǎng)絡(luò)。
IP協(xié)議只保證計(jì)算機(jī)能發(fā)送和接收分組數(shù)據(jù)。IP協(xié)議負(fù)責(zé)將消息從一個(gè)主機(jī)傳送到另一個(gè)主機(jī),消息在傳送的過(guò)程中被分割成一個(gè)個(gè)的小包
6.Java對(duì)TCP/IP協(xié)議的支持
- TCP/IP通信協(xié)議是一種可靠的網(wǎng)絡(luò)協(xié)議,它在通信的兩端各建立一個(gè)Socket,從而在通信的兩端之間形成網(wǎng)絡(luò)虛擬鏈路
- 一旦建立了虛擬的網(wǎng)絡(luò)鏈路,兩端的程序就可以通過(guò)虛擬鏈路進(jìn)行通信
- Java對(duì)基于TCP協(xié)議的網(wǎng)絡(luò)通信提供了良好的封裝,Java使用Socket對(duì)象來(lái)代表兩端的通信接口,并通過(guò)Socket產(chǎn)生IO流來(lái)進(jìn)行網(wǎng)絡(luò)通信
IP的概念
IP是互聯(lián)網(wǎng)上的每一臺(tái)計(jì)算機(jī)都有得一個(gè)唯一表示自己的標(biāo)記
IP地址使用4個(gè)8位的二進(jìn)制數(shù)據(jù)表示,每8位之間使用圓點(diǎn)隔開(kāi),每個(gè)8位整數(shù)可以轉(zhuǎn)換成一個(gè)0~255的十進(jìn)制整數(shù)
因此一般看到的IP地址類似:192.168.1.1
IP地址分類:
- IPv4:32位,分4段,0~255之間的十進(jìn)制表示
- IPv6:128位,分8段,0000~FFFF的十六進(jìn)制數(shù)值,冒號(hào)分割
如:1080:0:0:0:8:800:200C:417A
- IP地址 = 網(wǎng)絡(luò)地址 + 主機(jī)地址
- 網(wǎng)絡(luò)號(hào):用于識(shí)別主機(jī)所在的網(wǎng)絡(luò)
- 主機(jī)號(hào):用于識(shí)別該網(wǎng)絡(luò)的主機(jī)
什么是端口?
如果把IP地址比作一間房子 ,端口就是出入這間房子的門。真正的房子只有幾個(gè)門,但是一個(gè)IP地址的端口 可以有65536(即:2^16)個(gè)之多!端口是通過(guò)端口號(hào)來(lái)標(biāo)記的,端口號(hào)只有整數(shù),范圍是從0 到65535(2^16-1)
同一臺(tái)機(jī)器上不能有兩個(gè)程序使用同一個(gè)端口;
端口的分類:
- 公認(rèn)端口:0~1023,他們緊密綁定一些服務(wù)
- 注冊(cè)端口:1024~49151,松散綁定一些服務(wù)
- 動(dòng)態(tài)端口:49152~65535,動(dòng)態(tài)使用的端口,程序一般不會(huì)使用這些端口;
TCP協(xié)議
- TCP協(xié)議被稱作一種端對(duì)端協(xié)議
- 這是因?yàn)樗鼮閮膳_(tái)計(jì)算機(jī)之間的連接起了重要作用:當(dāng)一臺(tái)計(jì)算機(jī)需要與另一臺(tái)遠(yuǎn)程計(jì)算機(jī)連接時(shí),TCP協(xié)議會(huì)讓它們建立一個(gè)連接:用于發(fā)送和接收數(shù)據(jù)的虛擬鏈路。
- TCP協(xié)議負(fù)責(zé)收集這些信息包,并將其按適當(dāng)?shù)拇涡蚍藕脗魉?,在接收端收到后再將其正確地還原
- TCP協(xié)議保證了數(shù)據(jù)包在傳送中準(zhǔn)確無(wú)誤。TCP協(xié)議使用重發(fā)機(jī)制:當(dāng)一個(gè)通信實(shí)體發(fā)送一個(gè)消息給另一個(gè)通信實(shí)體后,需要收到另一個(gè)通信實(shí)體確認(rèn)信息,如果沒(méi)有收到另一個(gè)通信實(shí)體的確認(rèn)信息,則會(huì)再次重發(fā)剛才發(fā)送的信息
- 通過(guò)這種重發(fā)機(jī)制,TCP協(xié)議向應(yīng)用程序提供可靠的通信連接,使它能夠自動(dòng)適應(yīng)網(wǎng)上的各種變化。即使在 Internet 暫時(shí)出現(xiàn)堵塞的情況下,TCP也能夠保證通信的可靠
UDP協(xié)議
- UDP協(xié)議是一種不可靠的網(wǎng)絡(luò)協(xié)議
- 它在通信實(shí)例的兩端各建立一個(gè)Socket,但這兩個(gè)Socket之間并沒(méi)有虛擬鏈路,這兩個(gè)Socket只是發(fā)送、接收數(shù)據(jù)報(bào)的對(duì)象,Java提供了DatagramSocket對(duì)象作為基于UDP協(xié)議的Socket,使用DatagramPacket代表DatagramSocket發(fā)送、接收的數(shù)據(jù)報(bào)
發(fā)送端:在發(fā)送端,要在數(shù)據(jù)包對(duì)象中明確目的地IP及端口
DatagramSocket ds = new DatagramSocket();
byte[] by = “hello,udp”.getBytes();
DatagramPacket dp = new DatagramPacket(by,0,by.length,
InetAddress.getByName(“127.0.0.1”),10000);
ds.send(dp);
ds.close();
接收端:在接收端,要指定監(jiān)聽(tīng)的端口
DatagramSocket ds = new DatagramSocket(10000);
byte[] by = new byte[1024];
DatagramPacket dp = new DatagramPacket(by,by.length);
ds.receive(dp);
String str = new String(dp.getData() );
System.out.println(str+"--"+dp.getAddress());
ds.close();
- TCP協(xié)議:可靠,傳輸大小無(wú)限制,但是需要連接建立時(shí)間,差錯(cuò)控制開(kāi)銷大
- UDP協(xié)議:不可靠,差錯(cuò)控制開(kāi)銷較小,傳輸大小限制在64K以下,不需要建立連接
物理,比特流 網(wǎng)卡
數(shù)據(jù)鏈路,數(shù)據(jù)幀 交換機(jī)
網(wǎng)絡(luò),IP TCP上層?數(shù)據(jù) 數(shù)據(jù)包 路由器
傳輸,TCP上頭上層數(shù)據(jù) 數(shù)據(jù)段 防火墻
會(huì)話,
表示,
應(yīng)用 上層數(shù)據(jù) 48位2進(jìn)制 計(jì)算機(jī)
TCP/IP4 TCP/IP5 TCP/IP7
物理層 0,1 比特流
數(shù)據(jù)鏈路層
網(wǎng)絡(luò)層 數(shù)據(jù)包封裝結(jié)構(gòu)
傳輸層
會(huì)話層建立會(huì)話關(guān)系
TCP/
ARP轉(zhuǎn)為Mark地址
ICMP傳輸用戶協(xié)議
TCP需要同步才能傳輸數(shù)據(jù),安全性高/傳輸控制協(xié)議 三次握手 四次結(jié)束
HTTP傳輸協(xié)議
FTP文件傳輸協(xié)議
SMTP郵件傳輸協(xié)議
DNS將域名轉(zhuǎn)化為地址
UDP效率更快,但不安全/用戶數(shù)據(jù)協(xié)議
ARP將IP解析成Mark地址的過(guò)程
arp -a 為了防止欺騙,實(shí)行綁定地址
實(shí)現(xiàn)字節(jié)流和字符流分別實(shí)現(xiàn)客戶端,服務(wù)器返回
1.ServerSocket(服務(wù)端)
- ServerSocket對(duì)象用于監(jiān)聽(tīng)來(lái)自客戶端的Socket連接,如果沒(méi)有連接,它將一直處于等待狀態(tài)
- ServerSocket包含一個(gè)監(jiān)聽(tīng)來(lái)自客戶端連接請(qǐng)求的方法:
- Socket accept():如果接收到一個(gè)客戶端Socket的連接請(qǐng)求,該方法將返回一個(gè)與連客戶端Socket對(duì)應(yīng)的Socket,否則該方法將一直處于等待狀態(tài),線程也被阻塞
- 為了創(chuàng)建ServerSocket對(duì)象,ServerSocket類提供了如下幾個(gè)構(gòu)造器:
- ServerSocket(int port):用指定的端口port來(lái)創(chuàng)建一個(gè)ServerSocket
- 該端口應(yīng)該是有一個(gè)有效的端口整數(shù)值:0~65535
- ServerSocket(int port,int backlog):增加一個(gè)用來(lái)改變連接隊(duì)列長(zhǎng)度的參數(shù)backlog
- ServerSocket(int port,int backlog,InetAddress localAddr):在機(jī)器存在多個(gè) IP地址的情況下,允許通過(guò)localAddr這個(gè)參數(shù)來(lái)指定將ServerSocket綁定到指定的IP地址
- 服務(wù)端:建立服務(wù)端需要監(jiān)聽(tīng)一個(gè)端口
ServerSocket ss = new ServerSocket(9999);
Socket s = ss.accept ();
InputStream in = s.getInputStream();
byte[] buf = new byte[1024];
int num = in.read(buf);
String str = new String(buf,0,num);
System.out.println(s.getInetAddress().toString()+”:”+str);
s.close();
ss.close();
2.Socket(客戶端)
- 客戶端通??墒褂肧ocket的構(gòu)造器來(lái)連接到指定服務(wù)器,Socket通??墒褂萌缦聝蓚€(gè)構(gòu)造器:
- Socket(InetAddress/String remoteAddress, int port):創(chuàng)建連接到指定遠(yuǎn)程主機(jī)、遠(yuǎn)程端口的Socket,該構(gòu)造器沒(méi)有指定本地地址、本地端口,默認(rèn)使用本地主機(jī)的默認(rèn)IP地址,默認(rèn)使用系統(tǒng)動(dòng)態(tài)指定的IP地址
- Socket(InetAddress/String remoteAddress, int port, InetAddress localAddr, int localPort):創(chuàng)建連接到指定遠(yuǎn)程主機(jī)、遠(yuǎn)程端口的Socket,并指定本地IP地址和本地端口號(hào),適用于本地主機(jī)有多個(gè)IP地址的情形
- 客戶端:通過(guò)Socket建立對(duì)象并指定要連接的服務(wù)端主機(jī)以及端口
Socket s = new Socket(“192.168.1.1”,9999);
OutputStream out = s.getOutputStream();
out.write(“hello”.getBytes());
s.close();
- 當(dāng)客戶端、服務(wù)器端產(chǎn)生了對(duì)應(yīng)的Socket之后,程序無(wú)需再區(qū)分服務(wù)器、客戶端,而是通過(guò)各自的Socket進(jìn)行通信,Socket提供如下兩個(gè)方法來(lái)獲取輸入流和輸出流:
- InputStream getInputStream():返回該Socket對(duì)象對(duì)應(yīng)的輸入流,讓程序通過(guò)該輸入流從Socket中取出數(shù)據(jù)
- OutputStream getOutputStream():返回該Socket對(duì)象對(duì)應(yīng)的輸出流,讓程序通過(guò)該輸出流向Socket中輸出數(shù)據(jù)
實(shí)例一:下載網(wǎng)絡(luò)圖片保存到此項(xiàng)目目錄
package cn.http;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLConnection;
public class HttpPhoto {
@SuppressWarnings("resource")
public static void main(String[] args) {
//打開(kāi)url網(wǎng)址
String url = "http://t1.27270.com/uploads/150609/7-1506091506401R.jpg";
try {
URL uu = new URL(url);//創(chuàng)建URL對(duì)象
URLConnection uc = uu.openConnection();//返回URLConnection
uc.connect();//發(fā)起請(qǐng)求連接
InputStream in = uc.getInputStream();//輸入
byte[] bytes = new byte[1024];//字節(jié)儲(chǔ)存
int len = 0;
File f = new File("美女圖片.jpg");//將圖片保存跟目錄
FileOutputStream fos = new FileOutputStream(f);//輸出
//循環(huán)讀取
while((len = in.read(bytes))!=-1){
fos.write(bytes,0,len);
}
System.out.println("圖片下載成功!");
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
}
實(shí)例二:與網(wǎng)絡(luò)機(jī)器人聊天功能
package cn.http;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLConnection;
import java.util.Scanner;
/**
* 連接接口實(shí)現(xiàn)聊天功能
* JSON數(shù)據(jù)格式
* @author JEEP-711
*/
public class HttpCalling {
@SuppressWarnings({ "unused", "resource" })
public static void main(String[] args) {
String name = "咨詢助理";
Scanner sc = new Scanner(System.in);//接收進(jìn)控制鍵盤輸入
System.out.println("Hi,現(xiàn)在我們已經(jīng)是好友啦,開(kāi)始我們的聊天吧!");//提示
//循環(huán)輸入
while(true){
System.out.println("請(qǐng)輸入...");//提示
String user = sc.next();//用戶輸入內(nèi)容
//打開(kāi)url接口網(wǎng)址
String url = "http://www.tuling123.com/openapi/api?key=4c767f02ca7b44378156821ab35856df&info="+user;
try {
URL uu = new URL(url);//創(chuàng)建URL對(duì)象
URLConnection uc = uu.openConnection();//返回URLConnection
uc.connect();//發(fā)起請(qǐng)求連接
//讀取原文件
BufferedReader br = new BufferedReader(new InputStreamReader(uc.getInputStream()));
StringBuffer sb = new StringBuffer();
String s = "";
s = br.readLine();
String[] str = s.split(":");//分隔字符串
String[] strs = str[2].split("\"");
//for數(shù)組
for(String sr : strs){
System.out.println(name +"發(fā)來(lái)消息:"+strs[1]);
}
//JSONObject jc = new JSONObject(s);
//System.out.println(name +"發(fā)來(lái)消息:"+br.readLine());
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
實(shí)例三:網(wǎng)絡(luò)編程傳輸文件
package cn.socket;
import java.io.DataInputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.net.ServerSocket;
import java.net.Socket;
/**
* 服務(wù)端
* @author JEEP-711
*
*/
public class Servers extends ServerSocket{
private static final int PORT = 8000;//定義靜態(tài)整形常量端口號(hào)
private ServerSocket ss;//定義服務(wù)端
private Socket sk;//定義客戶端
private DataInputStream d;//定義
private FileOutputStream fp;//定義文件傳輸
//定義構(gòu)造方法并拋出異常
public Servers()throws Exception{
try {
try {
ss = new ServerSocket(PORT);//傳值-端口號(hào)
while(true){
sk = ss.accept();
d = new DataInputStream(sk.getInputStream());
//文件名和長(zhǎng)度
String fileName = d.readUTF();
long fileLeng = d.readLong();
fp =new FileOutputStream(new File("src\\" + fileName));
byte[] bytes = new byte[1024];//定義為1024個(gè)字節(jié)
int len = 0;//定義為0
//文件傳輸提示
System.out.println("----正在開(kāi)始接收文件<" + fileName +"&,文件大小為<" + fileLeng +"&----");
while(true){
int read =0;
read = d.read(bytes);
if(read == -1)
break;
len += read;
System.out.println("接收文件進(jìn)度" +100 * len/fileLeng +"%...");//文件接收提示
fp.write(bytes,0, read);//
fp.flush();//刷新
}
System.out.println("----接收文件<" + fileName +"&成功-------");
sk.close();//關(guān)閉流客戶端
}
}catch (Exception e) {
e.printStackTrace();
//統(tǒng)一出口
}finally {
//如果傳輸不等于空
if(d !=null)
d.close();//則關(guān)閉傳輸流
//如果文件傳輸不等于空
if(fp !=null)
fp.close();//則關(guān)閉傳輸文件流
ss.close();//關(guān)閉服務(wù)器流
}
}catch (Exception e) {
e.printStackTrace();
}
}
@SuppressWarnings("resource")
public static void main(String[] args) throws Exception{
new Servers();//調(diào)用Servers方法
}
}
package cn.socket;
import java.io.DataOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.net.Socket;
/**
* 客戶端
* @author JEEP-711
*
*/
public class Cilens extends Socket{
private static final String server_ip = "192.168.199.109";//定義靜態(tài)字符串常量IP地址
private static final int duankou = 8000;//定義靜態(tài)整形常量端口號(hào)
private Socket s;//定義服務(wù)器
private FileInputStream f;//定義文件
private DataOutputStream d;//定義傳輸
//構(gòu)造方法
public Cilens(){
try {
try {
s = new Socket(server_ip,duankou);//傳參數(shù)
//向服務(wù)端傳送文件
File file =new File("src\\test.doc");//文件在src目錄下
f = new FileInputStream(file);//傳文件
d = new DataOutputStream(s.getOutputStream());
//文件名和長(zhǎng)度
d.writeUTF(file.getName());//文件名稱
d.flush();//刷新
d.writeLong(file.length());//文件長(zhǎng)度
d.flush();//傳輸刷新
//傳輸文件
byte[] Bytes =new byte[1024];//定義byte1024的字節(jié)
int len = 0;//定義len為0
//循環(huán)
while((len = f.read(Bytes,0,Bytes.length)) &0){
d.write(Bytes,0, len);//字節(jié)從0到len
d.flush();//傳輸刷新
}
}catch (Exception e) {
e.printStackTrace();
}finally{
//如果文件不等于空
if(f !=null)
f.close();//則關(guān)閉流
//如果傳輸不等于空
if(d !=null)
d.close();//則關(guān)閉流
s.close();//關(guān)閉流
}
}catch (Exception e) {
e.printStackTrace();
}
}
@SuppressWarnings("resource")
public static void main(String[] args) throws Exception {
new Cilens();//調(diào)用方法
}
}
Copyright©2021 w3cschool編程獅|閩ICP備15016281號(hào)-3|閩公網(wǎng)安備35020302033924號(hào)
違法和不良信息舉報(bào)電話:173-0602-2364|舉報(bào)郵箱:jubao@eeedong.com
掃描二維碼
下載編程獅App
編程獅公眾號(hào)
聯(lián)系方式:
更多建議: