20175323 团队项目 服务器端函数功能与业务逻辑详解 20175323 团队项目服务器端函数功能与业务逻辑详解 Socket在服务器和客户端之间建立连接并进行数据交互的过程 编写代码实现socket收发消息的功能 程序运行结果 实践收获

本博客对于团队项目的服务器端程序的函数功能做出了解释,并对于整个应用系统的服务器端的业务逻辑做出了解释


Socket在服务器和客户端之间建立连接并进行数据交互的过程

流程图(时序图)

20175323  团队项目  服务器端函数功能与业务逻辑详解
20175323 团队项目服务器端函数功能与业务逻辑详解
Socket在服务器和客户端之间建立连接并进行数据交互的过程
编写代码实现socket收发消息的功能
程序运行结果
实践收获
预想的每一步的操作过程都已经体现在流程图中了

UML类图

所以总计需要四个类:客户端、服务器、发送、接收,客户端和服务器分别对发送和接收都有依赖关系
UML类图如下
20175323  团队项目  服务器端函数功能与业务逻辑详解
20175323 团队项目服务器端函数功能与业务逻辑详解
Socket在服务器和客户端之间建立连接并进行数据交互的过程
编写代码实现socket收发消息的功能
程序运行结果
实践收获

编写代码实现socket收发消息的功能

客户端程序

package com.wenqier.client;

import java.net.*;
import java.io.*;

//聊天过程用于发送信息的线程
class Send extends Thread {
	Socket socket;

	public Send(Socket sock) {
		this.socket = sock;
	}
	// 专门用于发送信息
	public void run() {
		DataOutputStream out;
		while (true) {
			BufferedReader input = new BufferedReader(new InputStreamReader(
					System.in));
			try {
				String str;
				str = input.readLine();
				out = new DataOutputStream(socket.getOutputStream());
				out.writeUTF(str);
			} catch (Exception e) {
			}
		}

	}
}

// 创建一个专门用于接收消息的线程
class Receive extends Thread {
	Socket socket;

	public Receive(Socket sock) {
		this.socket = sock;
	}

	public void run() {
		// 专门用于接收消息
		DataInputStream in;
		while (true) {
			try {
				in = new DataInputStream(socket.getInputStream());
				String str = in.readUTF();
				System.out.println(str);
			} catch (Exception e) {
			}
		}
	}
}

public class Client {

	static Socket socket;

	public static void main(String[] args) throws Exception {

		socket = new Socket("127.0.0.1", 5678);

		System.out.println("客户端.....");
		try {
			Send send = new Send(socket);
			Receive receive = new Receive(socket);
			// 打开线程
			send.start();
			receive.start();
		} catch (Exception e) {
		}
	}
}

服务器端程序

package com.wenqier.service;

import java.net.*;
import java.io.*;

//聊天过程中新建一个专门用于发送信息的线程
class Send extends Thread {
	Socket socket;

	public Send(Socket sock) {
		this.socket = sock;
	}
	// 专门用于发送信息
	public void run() {
		DataOutputStream out;
		while (true) {
			BufferedReader input = new BufferedReader(new InputStreamReader(
					System.in));
			try {
				String str;
				str = input.readLine();
				out = new DataOutputStream(socket.getOutputStream());
				out.writeUTF(str);
			} catch (Exception e) {
			}
		}

	}
}

// 创建一个专门用于接收消息的线程
class Receive extends Thread {
	Socket socket;

	public Receive(Socket sock) {
		this.socket = sock;
	}

	public void run() {
		// 专门用于接收消息
		DataInputStream in;
		while (true) {
			try {
				in = new DataInputStream(socket.getInputStream());
				String str = in.readUTF();
				System.out.println(str);
			} catch (Exception e) {
			}
		}
	}
}

public class Service {
	// 声明ServerSocket类对象
	static ServerSocket service;

	public static void main(String[] args) {
		try {
			service = new ServerSocket(5678);

			System.out.println("服务器端.....");
			Socket client = null;

			client = service.accept();

			Send send = new Send(client);
			Receive receive = new Receive(client);
			// 打开线程
			send.start();
			receive.start();
		} catch (Exception e) {
		}
	}
}

程序运行结果

运行程序在命令行里输出这个是客户端
20175323  团队项目  服务器端函数功能与业务逻辑详解
20175323 团队项目服务器端函数功能与业务逻辑详解
Socket在服务器和客户端之间建立连接并进行数据交互的过程
编写代码实现socket收发消息的功能
程序运行结果
实践收获
客户端发送消息hello!
20175323  团队项目  服务器端函数功能与业务逻辑详解
20175323 团队项目服务器端函数功能与业务逻辑详解
Socket在服务器和客户端之间建立连接并进行数据交互的过程
编写代码实现socket收发消息的功能
程序运行结果
实践收获
服务器端正常接收到了消息hello!,发回一个你好!
20175323  团队项目  服务器端函数功能与业务逻辑详解
20175323 团队项目服务器端函数功能与业务逻辑详解
Socket在服务器和客户端之间建立连接并进行数据交互的过程
编写代码实现socket收发消息的功能
程序运行结果
实践收获
客户端正常接收到了发来的你好
20175323  团队项目  服务器端函数功能与业务逻辑详解
20175323 团队项目服务器端函数功能与业务逻辑详解
Socket在服务器和客户端之间建立连接并进行数据交互的过程
编写代码实现socket收发消息的功能
程序运行结果
实践收获

实践收获

除了Java 的socket编程和多线程编程之外,通过查找资料我还有如下的收获

JAVA Socket和C Socket的比较

通过之前教材和本次实践学习的JAVA Socket与学长用例子给我讲socket的时候用的他编的C socket程序,我理解的两种socket的最主要不同有两个,就是面向对象与面向过程的不同和函数的封装的完备程度的不同。
我理解的面向对象与面向过程的不同最明显的就是C语言的socket程序,一般需要声明两个或者更多socket。这些套接字里必须要有一个socket调用accept方法监听客户端的连接请求,而accept方法返回的套接字描述符传给一个新的socket用来做数据交互,之前的socket继续监听。这样的机制能够保证服务器端一直有一个socket是监听状态。
20175323  团队项目  服务器端函数功能与业务逻辑详解
20175323 团队项目服务器端函数功能与业务逻辑详解
Socket在服务器和客户端之间建立连接并进行数据交互的过程
编写代码实现socket收发消息的功能
程序运行结果
实践收获
而Java socket只要一个套接字就可以同时进行监听与数据传输,因为它可以调用Serversocket对象的获取输入以及输出流的成员函数来创建线程,用创建的线程实现数据交互,而这个主函数本身还可以继续监听客户端的请求。
另外一方面就是函数的封装,Java socket的库函数(确切的说是包)封装的非常完备,实现双方的数据交互全部的步骤也不到两三步。而C语言写socket就比这个要繁琐
C语言写socket要这样,地址和端口的绑定和监听都要自己写,而且函数参数貌似比Java复杂
20175323  团队项目  服务器端函数功能与业务逻辑详解
20175323 团队项目服务器端函数功能与业务逻辑详解
Socket在服务器和客户端之间建立连接并进行数据交互的过程
编写代码实现socket收发消息的功能
程序运行结果
实践收获
用Java写tcp socket更加容易,目前更有助于我们理解计网学的tcp协议

客户端与服务器socket的比较

这个程序使用的是面向连接的socket,因此客户端和服务器都是socket但是有一些不同存在,就是服务器端要用accept方法接收客户端的连接请求
20175323  团队项目  服务器端函数功能与业务逻辑详解
20175323 团队项目服务器端函数功能与业务逻辑详解
Socket在服务器和客户端之间建立连接并进行数据交互的过程
编写代码实现socket收发消息的功能
程序运行结果
实践收获

实际生活中socket的使用与一部分思考

实际生活中的应用系统,用的大多是面向无连接的socket,即使用的是udp协议的socket。比如说我们用的微信和QQ。因为,udp虽然无连接、不可靠、尽最大努力交付,但是和tcp相比它的速度非常优秀,可以满足聊天的实时性的需求,而且微信发语音要的也是个速度。
但是我们为了准确而且安全,使用了tcp协议的面向连接的socket,所以后期加上密码算法之后,聊天的用户体验就可能会受到网速(收发数据)、计算机硬件(加解密与验证的速度)的制约,但是我们的程序规模又不是特别大,效果上会影响的可能没有想象的那么大。