学习socket网络编程,需要熟悉一些计算机网络的基本知识(互联网协议中的TCP和UDP协议)。
Java支持基于流的通信和基于包的通信。基于流的通信使用的就是TCP(传输控制协议)进行数据传输,基于包的通信使用的就是UDP(用户数据报协议)。因为TCP协议能够发现丢失的传输信息并进行重新发送(可靠,无损的服务),而UDP不能保证传输没有丢失(不可靠的服务),因此,Java程序中多采用基于流的通信。
下面,就进入简单demo吧
一、服务器端
要创建服务器,需要创建一个服务器套接字,即ServerSocket,并且把它附加到一个端口上,服务器就能从这个端口上进行监听。
这里我们任意选择一个没有被其它进程使用的端口3366.
1.创建服务器的套接字:
ServerSocket server = new ServerSocket(3366);
2.创建服务器后监听连接:
Socket socket = server.accept();
这个语句会一直等待,知道有一个客户端连接到了该服务器的套接字。
二、客户端
客户端连接服务器,需要指定连接的是哪一个主机(服务器),在这里我的服务器和客户端都是在我的本地,因此是localhost(虚拟机会让DNS将我的主机名解析成127.0.0.1),在这里不仅可以使用IP地址,也可以使用域名。
选择3366端口号进行连接,服务器监听的是这个端口号,能够发现客户端的连接请求。
Socket socket = new Socket("localhost", 3366);
就这几个方法很简单的。
下面是一个小例子
首先是服务端:
package network;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
public class Server implements Runnable{
private static final int PORT = 3366;
private ServerSocket server;
private Socket socket;
@Override
public void run() {
DataInputStream in = null;
DataOutputStream out = null;
try {
// 1.创建一个服务器套接字,端口号为 11111
server = new ServerSocket(PORT);
// 2.服务器监听这个端口的连接
socket = server.accept();
// 3.获取接收数据的输入输出流
in = new DataInputStream(socket.getInputStream());
out = new DataOutputStream(socket.getOutputStream());
while (true) {
// 4.读取输入流中的数据
byte[] buffer = new byte[100];
// 将客户端传输来的数据读入buffer缓存数组中
in.read(buffer);
System.out.println("服务器接收到客户端的信息:" + new String(buffer));
// 5.客户端作出回应
String response = "Word";
byte[] buf = response.getBytes();
out.write(buf);
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
然后是客户端
package network;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
public class Server implements Runnable{
private static final int PORT = 3366;
private ServerSocket server;
private Socket socket;
@Override
public void run() {
DataInputStream in = null;
DataOutputStream out = null;
try {
// 1.创建一个服务器套接字,端口号为 11111
server = new ServerSocket(PORT);
// 2.服务器监听这个端口的连接
socket = server.accept();
// 3.获取接收数据的输入输出流
in = new DataInputStream(socket.getInputStream());
out = new DataOutputStream(socket.getOutputStream());
while (true) {
// 4.读取输入流中的数据
byte[] buffer = new byte[100];
// 将客户端传输来的数据读入buffer缓存数组中
in.read(buffer);
System.out.println("服务器接收到客户端的信息:" + new String(buffer));
// 5.客户端作出回应
String response = "Word";
byte[] buf = response.getBytes();
out.write(buf);
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
然后启动这两个线程,
package network;
public class MyTest {
public static void main(String[] args) {
Server server = new Server();
Client client = new Client();
Thread t1 = new Thread(server);
Thread t2 = new Thread(client);
t1.start();
t2.start();
}
}
运行结果如下:
可以知道,服务器启动后一直在监听不会中断,每当客户端发送请求(信息)就会给出相应的响应。