【案例9-2】 字符串反转
【案例介绍】
1.案例描述
在使用软件或浏览网页时,总会查询一些数据,查询数据的过程其实就是客户端与服务器交互的过程。用户(客户端)将查询信息发送给服务器,服务器接收到查询消息后进行处理,将查询结果返回给用户(客户端)。本案例要求编写一个模拟客户端与服务端交互的程序,客户端向服务器传递一个字符串(键盘录入),服务器将字符串反转后写回,客户端再次接收到的是反转后的字符串。本案例要求使用多线程与TCP通信相关知识完成数据交互。
2.运行结果
【案例分析】
(1)根据任务描述可以知道该程序用TCP通信技术实现,所以第一条就是定义客户端,键盘录入数据定义Scanner来实现,然后创建客户端指定IP地址和端口号,之后获取输出流,与输入流,最后将字符串写到服务器并将反转后的结果读出来打印在控制台。
(2)实现服务端的代码编写,首先创建服务端绑定客户端的端口号,并用Server的accept()方法接受客户端的请求。
(3)服务端定义run()方法实现之后获取输入输出流,将客户端发送过来的数据读取出来并采用链式编程的思想将字符串反转后返回到客户端。
【案例实现】
(1)创建客户端,用于录入输入的数据。其代码具体如下所示。
Client.java
1. package chapter0902;
2. import java.io.BufferedReader;
3. import java.io.IOException;
4. import java.io.InputStreamReader;
5. import java.io.PrintStream;
6. import java.net.Socket;
7. import java.net.UnknownHostException;
8. import java.util.Scanner;
9. public class Client {
10. public static void main(String[] args) throws UnknownHostException,
11. IOException {
12. //创建键盘录入对象
13. Scanner sc = new Scanner(System.in);
14. //创建客户端,指定ip地址和端口号
15. Socket socket = new Socket("127.0.0.1", 54321);
16. BufferedReader br = new BufferedReader(new
17. InputStreamReader(socket.getInputStream())); //获取输入流
18. //获取输出流
19. PrintStream ps = new PrintStream(socket.getOutputStream());
20. //将字符串写到服务器去
21. ps.println(sc.nextLine());
22. System.out.println(br.readLine()); //将反转后的结果读出来
23. socket.close();
24. }
25. }
上述代码中,第14行代码创建客户端指定IP地址与端口号,第15~18行代码获取输入与输出流,第20行代码用于将字符串写到服务器中去。第21行代码用于将反转后的结果读取出来。
(2)创建服务端实现将客户端数据反转并返回到客户端,其代码如下所示。
Server.java
1. package chapter0902;
2. import java.io.BufferedReader;
3. import java.io.IOException;
4. import java.io.InputStreamReader;
5. import java.io.PrintStream;
6. import java.net.ServerSocket;
7. import java.net.Socket;
8. public class Server {
9. public static void main(String[] args) throws IOException {
10. ServerSocket server = new ServerSocket(54321);
11. System.out.println("服务器启动,绑定54321端口");
12. while(true) {
13. final Socket socket = server.accept(); //接受客户端的请求
14. new Thread() { //开启一条线程
15. public void run() {
16. try {
17. BufferedReader br = new BufferedReader(new
18. InputStreamReader
19. (socket.getInputStream())); //获取输入流
20. PrintStream ps = new PrintStream
21. (socket.getOutputStream());//获取输出流
22. //将客户端写过来的数据读取出来
23. String line = br.readLine();
24. line = new StringBuilder(line).
25. reverse().toString(); //链式编程
26. ps.println(line); //反转后写回去
27. socket.close();
28. } catch (IOException e) {
29. e.printStackTrace();
30. }
31. }
32. }.start();
33. }
34. }
35. }
上述代码中,第9行代码用于创建Server服务器绑定端口号。第12行代码用Server的accept()方法来接收客户端的请求。第22行代码用readLine()方法将客户端写过来的数据读取出来,第23~24行代码用链式编程的方式将字符串反转,第25行代码将反转后的字符串返回给客户端打印。