通过 Socket 实现 TCP 编程

一、Socket简介

Socket通信实现步骤

1.创建ServerSocket和Socket

2.打开连接到Socket的输入/输出流

3.按照协议对Socket进行读/写操作

4.关闭输入输出流、关闭Socket

二、编程实现基于TCP的Socket通信之服务端与客户端

服务器端:

1.创建ServerSocket对象,绑定监听端口

2.通过accept()方法监听客户端请求

3.连接建立后,通过输入流读取客户端发送的请求信息

4.通过输出流向客户端响应信息

5.关闭相关资源

 1 import java.io.BufferedReader;
 2 import java.io.IOException;
 3 import java.io.InputStream;
 4 import java.io.InputStreamReader;
 5 import java.net.ServerSocket;
 6 import java.net.Socket;
 7 
 8 /*
 9  * 基于TCP协议的Socket通信,实现用户登陆
10  * 服务器端
11  */
12 public class Server {
13     public static void main(String[] args) {
14         try {
15             //1.创建一个服务器端Socket,即ServerSocket,指定绑定的端口,并监听此端口
16             ServerSocket serverSocket = new ServerSocket(8888);
17             //2.调用accept()方法开始监听,等待客户端的连接
18             System.out.println("***服务器即将启动,等待客户端的连接***");
19             Socket socket = serverSocket.accept();
20             //3.获取输入流,并读取客户端信息
21             InputStream is = socket.getInputStream();//字节输入流
22             InputStreamReader isr = new InputStreamReader(is);//将字节流转换为字符流
23             BufferedReader br = new BufferedReader(isr);//为输入流添加缓冲
24             String info = null;
25             while((info=br.readLine())!=null) {//循环读取客户端的信息
26                 System.out.println("我是服务器,客户端说:" + info);
27             }
28             socket.shutdownInput();//关闭输入流
29             
30             //4.关闭资源
31             br.close();
32             isr.close();
33             is.close();
34             socket.close();
35             serverSocket.close();        
36         } catch (IOException e) {
37             // TODO Auto-generated catch block
38             e.printStackTrace();
39         }
40         
41     }
42 
43 }

客户端:

1.创建Socket对象,指明需要连接的服务器的地址和端口号

2.连接建立后,通过输出流向服务器发送请求信息

3.通过输入流获取服务器响应的信息

4.关闭相应资源

 1 import java.io.IOException;
 2 import java.io.OutputStream;
 3 import java.io.PrintWriter;
 4 import java.net.Socket;
 5 import java.net.UnknownHostException;
 6 
 7 /*
 8  * 客户端
 9  */
10 public class Client {
11     public static void main(String[] args) {
12         try {
13             //1.创建客户端Socket,指定服务器地址和端口
14             Socket socket = new Socket("localhost",8888);
15             //2.获取输出流,向服务器端发送信息
16             OutputStream os = socket.getOutputStream();//字节输出流
17             PrintWriter pw = new PrintWriter(os);
18             pw.write("用户名:admin;密码:123");
19             pw.flush();
20             socket.shutdownOutput();//关闭输出流
21             
22             //3.关闭资源
23             pw.close();
24             os.close();
25             socket.close();
26         } catch (UnknownHostException e) {
27             e.printStackTrace();
28         } catch (IOException e) {
29             e.printStackTrace();
30         }
31     }
32 }

三、完善用户登陆之服务器响应客户端

服务端:

 1 import java.io.BufferedReader;
 2 import java.io.IOException;
 3 import java.io.InputStream;
 4 import java.io.InputStreamReader;
 5 import java.io.OutputStream;
 6 import java.io.PrintWriter;
 7 import java.net.ServerSocket;
 8 import java.net.Socket;
 9 
10 /*
11  * 基于TCP协议的Socket通信,实现用户登陆
12  * 服务器端(需要早于客户端启动)
13  */
14 public class Server {
15     public static void main(String[] args) {
16         try {
17             //1.创建一个服务器端Socket,即ServerSocket,指定绑定的端口,并监听此端口
18             ServerSocket serverSocket = new ServerSocket(8888);
19             //2.调用accept()方法开始监听,等待客户端的连接
20             System.out.println("***服务器即将启动,等待客户端的连接***");
21             Socket socket = serverSocket.accept();
22             //3.获取输入流,并读取客户端信息
23             InputStream is = socket.getInputStream();//字节输入流
24             InputStreamReader isr = new InputStreamReader(is);//将字节流转换为字符流
25             BufferedReader br = new BufferedReader(isr);//为输入流添加缓冲
26             String info = null;
27             while((info=br.readLine())!=null) {//循环读取客户端的信息
28                 System.out.println("我是服务器,客户端说:" + info);
29             }
30             socket.shutdownInput();//关闭输入流
31             
32             //4.获取输出流,响应客户端的请求
33             OutputStream os = socket.getOutputStream();
34             PrintWriter pw = new PrintWriter(os);//包装为打印流
35             pw.write("欢迎您!");
36             pw.flush();//调用flush()方法将缓冲输出
37             
38             //5.关闭资源
39             pw.close();
40             os.close();
41             br.close();
42             isr.close();
43             is.close();
44             socket.close();
45             serverSocket.close();        
46         } catch (IOException e) {
47             // TODO Auto-generated catch block
48             e.printStackTrace();
49         }
50         
51     }
52 
53 }

客户端:

 1 import java.io.BufferedReader;
 2 import java.io.IOException;
 3 import java.io.InputStream;
 4 import java.io.InputStreamReader;
 5 import java.io.OutputStream;
 6 import java.io.PrintWriter;
 7 import java.net.ServerSocket;
 8 import java.net.Socket;
 9 
10 /*
11  * 基于TCP协议的Socket通信,实现用户登陆
12  * 服务器端(需要早于客户端启动)
13  */
14 public class Server {
15     public static void main(String[] args) {
16         try {
17             //1.创建一个服务器端Socket,即ServerSocket,指定绑定的端口,并监听此端口
18             ServerSocket serverSocket = new ServerSocket(8888);
19             //2.调用accept()方法开始监听,等待客户端的连接
20             System.out.println("***服务器即将启动,等待客户端的连接***");
21             Socket socket = serverSocket.accept();
22             //3.获取输入流,并读取客户端信息
23             InputStream is = socket.getInputStream();//字节输入流
24             InputStreamReader isr = new InputStreamReader(is);//将字节流转换为字符流
25             BufferedReader br = new BufferedReader(isr);//为输入流添加缓冲
26             String info = null;
27             while((info=br.readLine())!=null) {//循环读取客户端的信息
28                 System.out.println("我是服务器,客户端说:" + info);
29             }
30             socket.shutdownInput();//关闭输入流
31             
32             //4.获取输出流,响应客户端的请求
33             OutputStream os = socket.getOutputStream();
34             PrintWriter pw = new PrintWriter(os);//包装为打印流
35             pw.write("欢迎您!");
36             pw.flush();//调用flush()方法将缓冲输出
37             
38             //5.关闭资源
39             pw.close();
40             os.close();
41             br.close();
42             isr.close();
43             is.close();
44             socket.close();
45             serverSocket.close();        
46         } catch (IOException e) {
47             // TODO Auto-generated catch block
48             e.printStackTrace();
49         }
50         
51     }
52 
53 }

四、使用多线程实现多客户端的通信

应用多线程来实现服务器与多客户端之间的通信

基本步骤:

1.服务器端创建ServerSocket,循环调用accept()等待客户端连接

2.客户端创建一个socket并请求和服务器端连接

3.服务器端接受客户端请求,创建socket与该客户建立专线连接

4.建立连接的两个socket在一个单独的线程上对话

5.服务器端继续等待新的连接

服务器线程处理类:

 1 import java.io.BufferedReader;
 2 import java.io.IOException;
 3 import java.io.InputStream;
 4 import java.io.InputStreamReader;
 5 import java.io.OutputStream;
 6 import java.io.PrintWriter;
 7 import java.net.Socket;
 8 
 9 /*
10  * 服务器线程处理类
11  */
12 public class ServerThread extends Thread {
13     // 和本线程相关的Socket
14     Socket socket = null;
15 
16     public ServerThread(Socket socket) {
17         this.socket = socket;
18     }
19     
20     //线程执行的操作,响应客户端的请求
21     public void run(){
22         InputStream is=null;
23         InputStreamReader isr=null;
24         BufferedReader br=null;
25         OutputStream os=null;
26         PrintWriter pw=null;
27         try {
28             //获取输入流,并读取客户端信息
29             is = socket.getInputStream();
30             isr = new InputStreamReader(is);
31             br = new BufferedReader(isr);
32             String info=null;
33             while((info=br.readLine())!=null){//循环读取客户端的信息
34                 System.out.println("我是服务器,客户端说:"+info);
35             }
36             socket.shutdownInput();//关闭输入流
37             //获取输出流,响应客户端的请求
38             os = socket.getOutputStream();
39             pw = new PrintWriter(os);
40             pw.write("欢迎您!");
41             pw.flush();//调用flush()方法将缓冲输出
42         } catch (IOException e) {
43             e.printStackTrace();
44         }finally{
45             //关闭资源
46             try {
47                 if(pw!=null)
48                     pw.close();
49                 if(os!=null)
50                     os.close();
51                 if(br!=null)
52                     br.close();
53                 if(isr!=null)
54                     isr.close();
55                 if(is!=null)
56                     is.close();
57                 if(socket!=null)
58                     socket.close();
59             } catch (IOException e) {
60                 e.printStackTrace();
61             }
62         }
63     }
64 }

修改服务器端:

 1 import java.io.BufferedReader;
 2 import java.io.IOException;
 3 import java.io.InputStream;
 4 import java.io.InputStreamReader;
 5 import java.io.OutputStream;
 6 import java.io.PrintWriter;
 7 import java.net.InetAddress;
 8 import java.net.ServerSocket;
 9 import java.net.Socket;
10 
11 /*
12  * 基于TCP协议的Socket通信,实现用户登陆
13  * 服务器端(需要早于客户端启动)
14  */
15 public class Server {
16     public static void main(String[] args) {
17         try {
18             //1.创建一个服务器端Socket,即ServerSocket,指定绑定的端口,并监听此端口
19             ServerSocket serverSocket = new ServerSocket(8888);
20             
21             Socket socket = null;
22             //记录客户端的数量
23             int count = 0;
24             System.out.println("***服务器即将启动,等待客户端的连接***");
25             //循环监听等待客户端的连接
26             while (true) {
27                 //2.调用accept()方法开始监听,等待客户端的连接
28                 socket = serverSocket.accept();
29                 //创建一个新的线程
30                 ServerThread serverThread = new ServerThread(socket);
31                 //启动线程
32                 serverThread.start();
33                 
34                 count++;//统计客户端的数量
35                 System.out.println("输出客户端的数量:" + count);
36                 InetAddress address = socket.getInetAddress();
37                 System.out.println("当前客户端的IP:" + address.getHostAddress());
38             }
39             
40             
41             
42                         
43             /*
44             //3.获取输入流,并读取客户端信息
45             InputStream is = socket.getInputStream();//字节输入流
46             InputStreamReader isr = new InputStreamReader(is);//将字节流转换为字符流
47             BufferedReader br = new BufferedReader(isr);//为输入流添加缓冲
48             String info = null;
49             while((info=br.readLine())!=null) {//循环读取客户端的信息
50                 System.out.println("我是服务器,客户端说:" + info);
51             }
52             socket.shutdownInput();//关闭输入流
53             
54             //4.获取输出流,响应客户端的请求
55             OutputStream os = socket.getOutputStream();
56             PrintWriter pw = new PrintWriter(os);//包装为打印流
57             pw.write("欢迎您!");
58             pw.flush();//调用flush()方法将缓冲输出
59             
60             //5.关闭资源
61             pw.close();
62             os.close();
63             br.close();
64             isr.close();
65             is.close();
66             socket.close();
67             */
68             
69             
70             //serverSocket.close();
71             
72         } catch (IOException e) {
73             // TODO Auto-generated catch block
74             e.printStackTrace();
75         }
76         
77     }
78 
79 }

修改客户端:

 1 import java.io.BufferedReader;
 2 import java.io.IOException;
 3 import java.io.InputStream;
 4 import java.io.InputStreamReader;
 5 import java.io.OutputStream;
 6 import java.io.PrintWriter;
 7 import java.net.Socket;
 8 import java.net.UnknownHostException;
 9 
10 /*
11  * 客户端
12  */
13 public class Client {
14     public static void main(String[] args) {
15         try {
16             //1.创建客户端Socket,指定服务器地址和端口
17             Socket socket = new Socket("localhost",8888);
18             //2.获取输出流,向服务器端发送信息
19             OutputStream os = socket.getOutputStream();//字节输出流
20             PrintWriter pw = new PrintWriter(os);
21             pw.write("用户名:admin;密码:123");
22             pw.flush();
23             socket.shutdownOutput();//关闭输出流
24             
25             //3.获取输入流,并读取服务器端的响应信息
26             InputStream is = socket.getInputStream();//字节输入流
27             BufferedReader br = new BufferedReader(
28                     new InputStreamReader(is));//将字节流转换为字符流,为输入流添加缓冲
29             String info = null;
30             while((info=br.readLine())!=null) {//循环读取客户端的信息
31                 System.out.println("我是客户端,服务器说:" + info);
32             }
33             
34             //4.关闭资源
35             br.close();
36             is.close();
37             pw.close();
38             os.close();
39             socket.close();
40         } catch (UnknownHostException e) {
41             e.printStackTrace();
42         } catch (IOException e) {
43             e.printStackTrace();
44         }
45     }
46 }

 

转载于:https://www.cnblogs.com/injoyisme/p/10631956.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
C语言是一种广泛应用于系统编程编程语言,具备强大的功能和灵活性。在C语言中,可以使用socket编程实现TCP端口扫描器来检测目标主机上的开放端口。 TCP端口扫描器是一种网络工具,用于探测目标主机上开放的TCP端口,这些开放的端口可以用来建立网络连接。TCP端口扫描器通过尝试建立TCP连接并检查连接的结果,从而确定哪些端口是开放的。 要实现TCP端口扫描器,需要借助C语言的socket库函数。首先,我们需要创建一个socket,调用socket()函数来创建一个套接字。然后,我们可以使用connect()函数来尝试连接目标主机的端口。如果连接成功,表示该端口是开放的,如果连接失败,则表示该端口是关闭或被防火墙限制。 以下是一个简单的C语言代码示例,演示了如何实现TCP端口扫描器: ```c #include <stdio.h> #include <stdlib.h> #include <unistd.h> #include <sys/socket.h> #include <arpa/inet.h> int main(int argc, char *argv[]) { if (argc != 3) { printf("Usage: %s <IP> <port>\n", argv[0]); return 1; } const char *ip = argv[1]; int port = atoi(argv[2]); struct sockaddr_in address; address.sin_family = AF_INET; address.sin_addr.s_addr = inet_addr(ip); address.sin_port = htons(port); int sockfd = socket(AF_INET, SOCK_STREAM, 0); if (sockfd < 0) { perror("socket creation failed"); return 1; } if (connect(sockfd, (struct sockaddr*)&address, sizeof(address)) == 0) { printf("Port %d is open\n", port); } else { printf("Port %d is closed\n", port); } close(sockfd); return 0; } ``` 以上代码中,首先检查命令行参数,确保传入了目标主机的IP地址和要扫描的端口号。然后,通过socket()函数创建一个套接字,并使用connect()函数尝试连接指定的IP地址和端口号。最后,根据连接的结果输出相应的信息,然后关闭套接字。 需要注意的是,该代码只能检测单个端口的状态。如果需要扫描多个端口,可以使用循环将上述代码包裹起来,并逐个尝试不同的端口号。 综上所述,以上是使用C语言以socket编程实现TCP端口扫描器的简单示例。通过这种方式,我们可以方便地检测目标主机上哪些端口是开放的,有助于网络安全评估和漏洞扫描等操作。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值