socket位于TCP/IP协议的传输层协议。相对于应用层的http协议,更低了一层。
通过服务员与客人的交互,学习一下socket
一、第一个场景
1、服务器端代码:
package me.net;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.net.ServerSocket;
import java.net.Socket;
/**
* Socket作用就是client端与server端通信。可以理解成客人与服务员之间以一定的规则说话。
*
* 场景1:一个客人,一个服务员。
*
* @author 3111
*
*/
public class ServerA {
/**
* 服务员,提供服务
*
* 创建server端过程:Server端运行使用的ip为当前设备的ip,端口号可以随便指定。不要和保留的重复。
* 雇佣一个服务员,告诉服务员,站在大门口,凡是在大门口进来的都是客人,后门进的,不是客人。大门口进来的,要打招呼。
*
* @param args
* @throws IOException
*/
public static void main(String[] args) {
// 指定一个端口号,这就是大门口
try {
ServerSocket serverSocket = new ServerSocket(9999);
// 等客来
Socket socket = serverSocket.accept();
System.err.println( "有人来了,看样子是本地人。ip是:" + socket.getInetAddress()
+ "。端口号是:" + socket.getPort());
// server端,向外输出数据。来客了,服务员得说话
OutputStream os = socket.getOutputStream();
// 封装一下
DataOutputStream dos = new DataOutputStream(os);
// 向客户端说一句话,你连上来了。
dos.writeUTF( "欢迎光临,你已经连上了!看样子你是本地人:你ip是:" + socket.getInetAddress()
+ "。你的端口号是:" + socket.getPort());
dos.writeUTF( "大牛笔记!www.weixuehao.com" );
dos. flush ();
// 下面就是释放各种资源了。
// 关dos,os,socket
dos.close();
os.close();
socket.close();
serverSocket.close();
} catch (IOException e) {
System.err.println(e.getMessage());
}
}
}
2、客户端代码:
package me.net;
import java.io.DataInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.Socket;
public class ClientA {
/**
* 连上socket。告诉socket,连什么ip,什么端口。然后就行了。 客人要知道,今晚去哪吃,进哪个门才对。
*
* @param args
*/
public static void main(String[] args) {
try {
// ip,端口,哪个店铺的,哪个大门。
Socket socket = new Socket( "localhost" , 9999);
// 客户端收到服务器的消息,所以是输入。客人刚进门,听到服务员说话。
InputStream is = socket.getInputStream();
DataInputStream dis = new DataInputStream(is);
// 看看收到服务器端什么东西
System.err.println(dis.readUTF());
System.err.println(dis.readUTF());
// 释放资源
dis.close();
is.close();
socket.close();
} catch (IOException e) {
System.err.println(e.getMessage());
}
}
}
二、第二个场景
1、服务器端代码:
package me.net;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.net.ServerSocket;
import java.net.Socket;
/**
* Socket作用就是client端与server端通信。可以理解成客人与服务员之间以一定的规则说话。
*
* 场景2:多个客人,一个服务员。来一个客人,说一句话。其实就是加个循环语句。
*
* @author 3111
*
*/
public class ServerB {
/**
* 服务员,提供服务
*
* 创建server端过程:Server端运行使用的ip为当前设备的ip,端口号可以随便指定。不要和保留的重复。
* 雇佣一个服务员,告诉服务员,站在大门口,凡是在大门口进来的都是客人,后门进的,不是客人。大门口进来的,要打招呼。
*
* @param args
* @throws IOException
*/
public static void main(String[] args) {
// 指定一个端口号,这就是大门口
try {
ServerSocket serverSocket = new ServerSocket(9999);
// 在这里加个循环语句,服务员一直在大门口站着
while (true) {
// 等客来
Socket socket = serverSocket.accept();
System.err
.println( "有人来了,看样子是本地人。ip是:" + socket.getInetAddress()
+ "。端口号是:" + socket.getPort());
// server端,向外输出数据。来客了,服务员得说话
OutputStream os = socket.getOutputStream();
// 封装一下
DataOutputStream dos = new DataOutputStream(os);
// 向客户端说一句话,你连上来了。
dos.writeUTF( "欢迎光临,你已经连上了!看样子你是本地人:你ip是:"
+ socket.getInetAddress() + "。你的端口号是:"
+ socket.getPort());
dos.writeUTF( "大牛笔记!www.weixuehao.com" );
dos. flush ();
// 下面就是释放各种资源了。
// 关dos,os,socket
dos.close();
os.close();
socket.close();
}
// serverSocket.close();
} catch (IOException e) {
System.err.println(e.getMessage());
}
}
}
2、客户端代码:
package me.net;
import java.io.DataInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.Socket;
public class ClientB {
/**
* 连上socket。告诉socket,连什么ip,什么端口。然后就行了。 客人要知道,今晚去哪吃,进哪个门才对。
*
* @param args
*/
public static void main(String[] args) {
try {
// ip,端口,哪个店铺的,哪个大门。
Socket socket = new Socket( "localhost" , 9999);
// 客户端收到服务器的消息,所以是输入。客人刚进门,听到服务员说话。
InputStream is = socket.getInputStream();
DataInputStream dis = new DataInputStream(is);
// 看看服务员说什么了
System.err.println(dis.readUTF());
System.err.println(dis.readUTF());
// 释放资源
dis.close();
is.close();
socket.close();
} catch (IOException e) {
System.err.println(e.getMessage());
}
}
}
三、第三个场景
1、服务器端代码:
package me.net;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.ServerSocket;
import java.net.Socket;
/**
* Socket作用就是client端与server端通信。可以理解成客人与服务员之间以一定的规则说话。
*
* 场景3:一个客人,一个服务员。来一个客人,服务员只说一句话。不太过瘾?客人也要说话,然后 服务员给一个响应的反馈,类似于机器人。
* 或可以理解成,微信的关键词,输入,然后返回对应的内容。
*
* @author 3111
*
*/
public class ServerC {
/**
* 服务员,提供服务
*
* 创建server端过程:Server端运行使用的ip为当前设备的ip,端口号可以随便指定。不要和保留的重复。
* 雇佣一个服务员,告诉服务员,站在大门口,凡是在大门口进来的都是客人,后门进的,不是客人。大门口进来的,要打招呼。
*
* @param args
*/
public static void main(String[] args) {
// 指定一个端口号,这就是大门口
try {
ServerSocket serverSocket = new ServerSocket(9999);
// 在这里加个循环语句,服务员一直在大门口站着
// 等客来
Socket socket = serverSocket.accept();
System.err.println( "有人来了,看样子是本地人。ip是:" + socket.getInetAddress()
+ "。端口号是:" + socket.getPort());
// server端,向外输出数据。来客了,服务员得向客人说话
OutputStream os = socket.getOutputStream();
// 封装一下
DataOutputStream dos = new DataOutputStream(os);
// server端,接收数据。听听客人说什么话。
InputStream is = socket.getInputStream();
DataInputStream dis = new DataInputStream(is);
String clientSay = "" ;
while (true) {
// 服务员一直在听客人说什么
clientSay = dis.readUTF();
System.err.println( "这小子说:" + clientSay);
if (clientSay.equals( "bye" )) {
break ;
}
// 向客户端说一句话,你连上来了。
dos.writeUTF( "欢迎光临,你已经连上了!看样子你是本地人:你ip是:"
+ socket.getInetAddress() + "。你的端口号是:"
+ socket.getPort());
dos.writeUTF( "大牛笔记!www.weixuehao.com" );
dos.writeUTF( "小子,你@#$@#$……再说一遍 #" + clientSay + "## 试试!" );
dos. flush ();
}
// 下面就是释放各种资源了。
// 关dos,os,socket
dos.close();
os.close();
socket.close();
serverSocket.close();
} catch (IOException e) {
System.err.println(e.getMessage());
}
}
}
2、客户端代码:
package me.net;
import java.io.BufferedReader;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.net.Socket;
public class ClientC {
/**
* 连上socket。告诉socket,连什么ip,什么端口。然后就行了。 客人要知道,今晚去哪吃,进哪个门才对。
*
* @param args
*/
public static void main(String[] args) {
try {
// ip,端口,哪个店铺的,哪个大门。
Socket socket = new Socket( "localhost" , 9999);
// 客户端收到服务器的消息,所以是输入。客人刚进门,听到服务员说话。
InputStream is = socket.getInputStream();
DataInputStream dis = new DataInputStream(is);
// 客人向服务员说...
OutputStream os = socket.getOutputStream();
DataOutputStream dos = new DataOutputStream(os);
// 客人自己打字。接收键盘的输入读取键盘输入流
InputStreamReader isr = new InputStreamReader(System.in);
// 封装键盘输入流
BufferedReader br = new BufferedReader(isr);
String clientSay = "" ;
while (true) {
// 所以下面需要客人自己说了,自己打字了
clientSay = br.readLine();
// 这个位置,最好和服务员那对应。
if (clientSay.equals( "bye" )) {
break ;
}
// 告诉客服你刚才想什么了
dos.writeUTF(clientSay);
dos. flush ();
// 听听服务员说什么了,这里输出和服务员那里数量要一样。要不然,就卡在这里了。
System.err.println(dis.readUTF());
System.err.println(dis.readUTF());
System.err.println(dis.readUTF());
}
// 释放资源
dis.close();
is.close();
socket.close();
} catch (IOException e) {
System.err.println(e.getMessage());
}
}
}
四、第四个场景
1、服务器端代码:
package me.net;
import java.io.BufferedReader;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.net.ServerSocket;
import java.net.Socket;
/**
* Socket作用就是client端与server端通信。可以理解成客人与服务员之间以一定的规则说话。
*
* 场景4:一个客人,一个服务员。聊会天吧。俩人都说。都听。
* 也就是服务员有俩线程。客人也有俩线程。服务员的听线程,对应客人的说线程。服务员的说线程,对应客人的听线程。
*
* @author 3111
*
*/
public class ServerD {
/**
* 服务员,提供服务
*
* 创建server端过程:Server端运行使用的ip为当前设备的ip,端口号可以随便指定。不要和保留的重复。
* 雇佣一个服务员,告诉服务员,站在大门口,凡是在大门口进来的都是客人,后门进的,不是客人。大门口进来的,要打招呼。
*
* @param args
* @throws IOException
*/
public static void main(String[] args) {
// 指定一个端口号,这就是大门口
try {
ServerSocket serverSocket = new ServerSocket(9999);
// 在这里加个循环语句,服务员一直在大门口站着
// 等客来
Socket socket = serverSocket.accept();
System.err.println( "有人来了,看样子是本地人。ip是:" + socket.getInetAddress()
+ "。端口号是:" + socket.getPort());
// server端,向外输出数据。来客了,服务员得向客人说话
OutputStream os = socket.getOutputStream();
// 封装一下
DataOutputStream dos = new DataOutputStream(os);
// server端,接收数据。听听客人说什么话。
InputStream is = socket.getInputStream();
DataInputStream dis = new DataInputStream(is);
new ServerIsListening(dis).start();
new ServerIsSaying(dos).start();
// 下面就是释放各种资源了。
// 关dos,os,socket
// dos.close();
// os.close();
// socket.close();
// serverSocket.close();
} catch (IOException e) {
System.err.println(e.getMessage());
}
}
}
class ServerIsListening extends Thread {
private DataInputStream dis;
public ServerIsListening(DataInputStream dis) {
this.dis = dis;
}
public void run() {
String clientSay = "" ;
try {
while (true) {
clientSay = dis.readUTF();
System.err.println( "客人说:" + clientSay);
if (clientSay.equals( "bye" )) {
System.err.println( "客官慢走~" );
System. exit (0);
}
}
} catch (Exception e) {
System.err.println(e.getMessage());
}
}
}
class ServerIsSaying extends Thread {
private DataOutputStream dos;
public ServerIsSaying(DataOutputStream dos) {
this.dos = dos;
}
public void run() {
InputStreamReader isr = new InputStreamReader(System.in);
BufferedReader br = new BufferedReader(isr);
String serverSay = "" ;
try {
while (true) {
serverSay = br.readLine();
dos.writeUTF(serverSay);
if (dos.equals( "bye" )) {
System.err.println( "不好意思,我下班了!" );
System. exit (0);
}
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
2、客户端代码:
package me.net;
import java.io.BufferedReader;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.net.Socket;
public class ClientD {
/**
* 连上socket。告诉socket,连什么ip,什么端口。然后就行了。 客人要知道,今晚去哪吃,进哪个门才对。
*
* @param args
*/
public static void main(String[] args) {
try {
// ip,端口,哪个店铺的,哪个大门。
Socket socket = new Socket( "localhost" , 9999);
// 客户端收到服务器的消息,所以是输入。客人刚进门,听到服务员说话。
InputStream is = socket.getInputStream();
DataInputStream dis = new DataInputStream(is);
// 客人向服务员说...
OutputStream os = socket.getOutputStream();
DataOutputStream dos = new DataOutputStream(os);
new ClientSay(dos).start();
new ClientListen(dis).start();
// //释放资源
// dis.close();
// is.close();
// socket.close();
} catch (IOException e) {
System.err.println(e.getMessage());
}
}
}
class ClientListen extends Thread {
private DataInputStream dis;
public ClientListen(DataInputStream dis) {
this.dis = dis;
}
public void run() {
String serverSay = "" ;
try {
while (true) {
serverSay = dis.readUTF();
System.err.println( "服务员说:" + serverSay);
if (serverSay.equals( "bye" )) {
System.err.println( "服务员下班走人了。" );
System. exit (0);
}
}
} catch (Exception e) {
e.getMessage();
}
}
}
class ClientSay extends Thread {
private DataOutputStream dos;
public ClientSay(DataOutputStream dos) {
this.dos = dos;
}
public void run() {
InputStreamReader isr = new InputStreamReader(System.in);
BufferedReader br = new BufferedReader(isr);
String str = "" ;
try {
while (true) {
str = br.readLine();
dos.writeUTF(str);
if (str.equals( "bye" )) {
System.err.println( "客人自己走了" );
System. exit (0);
}
}
} catch (Exception e) {
}
}
}