TCP/IP:传输控制协议/网间协议,是一个工业标准的协议集,它是为广域网(WANs)设计的
UDP:(User Data Protocol,用户数据报协议)是与tcp相对应的协议.它是属于TCP/Ip协议族中的一种.
Socket:应用层与TCP/IP协议族通信的中间软件抽象层,它是一组接口.在设计模式中,Socket其实就是一个门面模式,他把复杂的TCP/IP协议族隐藏在Socket接口后面.对用户来说,一组简单的接口就是全部,让Socket族组织数据,一符合指定的协议.在这里插入图片描述
单向通讯,先启动服务端,在启动客户端
public class Server {
public static void main(String[] args) throws Exception {
//监听指定的端口
ServerSocket server =new ServerSocket(9999);
//server将一直等待连接的到来
System.out.println("server将一直等待连接的到来");
Socket socket=server.accept();
//建立好连接后,从socket总获取输入流,并建立缓冲区进行读取.(从socket里面读出)
InputStream in=socket.getInputStream();
byte[] bs=new byte[1024];
StringBuffer str=new StringBuffer();
int len;
while((len=in.read(bs))!=-1){
str.append(new String(bs,0,len,"utf-8"));
}
System.out.println("来自客户端的消息:"+str);
in.close();
socket.close();
server.close();
}
}
public class Client {
public static void main(String[] args) throws Exception{
String ip="127.0.0.1";
//与服务器建立连接
Socket socket=new Socket(ip, 9999);
//建立连接后获得输出流
OutputStream out=socket.getOutputStream();
String message="哈哈哈哈哈哈哈";
//建立连接后获得输出流(往socket里面写入)
out.write(message.getBytes("utf-8"));
out.close();
socket.close();
}
双向通讯,先启动服务端,在启动客户端
public class Server {
public static void main(String[] args) throws Exception {
//监听指定的端口
ServerSocket server=new ServerSocket(9999);
System.out.println("server将一直等待连接的到来");
Socket socket=server.accept();
//建立好连接之后,从socket中获取流,并建立换缓冲区进行读取
InputStream in=socket.getInputStream();
byte[] bs=new byte[1024];
int len;
StringBuffer str=new StringBuffer();
//只有当客户端关闭它的输出流的时候,服务端才能取得结尾-1;
while((len=in.read(bs))!=-1){
//注意指定编码格式,发送方和接收方一定要统一,用utf-8
str.append(new String(bs,0,len,"utf-8"));
}
System.out.println("来自客户端的消息:"+str);
OutputStream out=socket.getOutputStream();
out.write("嗨,客户端!我已经收到消息了.".getBytes("utf-8"));
in.close();
out.close();
server.close();
}
}
public class Client {
public static void main(String[] args) throws Exception{
//连接服务器
Socket socket=new Socket("127.0.0.1",9999);
//建立连接后获得输出流
OutputStream out =socket.getOutputStream();
String message ="你好,我是client";
socket.getOutputStream().write(message.getBytes("utf-8"));
//通过shutdownInput高速服务器已经发送完数据,后续只能接收数据
socket.shutdownOutput();
InputStream in =socket.getInputStream();
byte[] bs=new byte[1024];
int len;
StringBuffer str=new StringBuffer();
while((len=in.read(bs))!=-1){
str.append(new String(bs,0,len,"utf-8"));
}
System.out.println("来自服务端:"+str);
in.close();
out.close();
socket.close();
}
}
调用Socket的shutdownOutput()方法,底层会告知服务端我这边已经写完了,那么服务端收到消息后,就能知道已经读取完消息,如果服务端有要返回给客户的消息那么就可以通过服务端的输出流发送给客户端,如果没有,直接关闭Socket。
这种方式通过关闭客户端的输出流,告知服务端已经写完了,虽然可以读到服务端发送的消息,但是还是有一点点缺点:
不能再次发送消息给服务端,如果再次发送,需要重新建立Socket连接
这个缺点,在访问频率比较高的情况下将是一个需要优化的地方。
ISO的七层模型:物理层 ,数据连接层,网络层,传输层,表示层,会话层,应用层
Socket属于传输层,它是对Tcp/ip协议的实现,包含tcp/udp.它是通讯协议的基础,Http协议需要Socket支持,以Socket为基础
Socket通讯的特点:
开启端口.该通讯是长连接的通讯,很容易被防火墙拦截.可以通过心跳机制来实现,开发难度大
传输的数据一般是字符串,可读性不强
socket端口不便于退的推广
性能相对应其他的通信协议是最优的
http属于应用层的协议,是对socket进行封装