Socket学习

2019-10-06  本文已影响0人  hekirakuno

socket是网络间进程通信的一种实现方式。

下图就是socket的原理图。


socket流程图

那么socket在哪里呢?又是服务于谁?
看下图:


socket抽象层的位置

我们使用java来做一次最简单的通信模拟吧。
服务端代码:

public class Server {
    public static void main(String[] args){
        try {
            System.out.println("【服务端:】服务端启动!");
            //监听端口为8080的连接(当不传参数时,默认绑定的服务器ip为127.0.0.1)
            ServerSocket server = new ServerSocket(8080);
            //建立socket通道(accept方法是阻塞方法)
            Socket socket = server.accept();
            System.out.println("【服务端:】监听到客户端连接!"+socket.getInetAddress());
            //读取数据流
            InputStream inputStream = socket.getInputStream();
            InputStreamReader inputStreamReader = new InputStreamReader(inputStream);
            BufferedReader bufferedReader = new BufferedReader(inputStreamReader);

            //read方法是阻塞方法
            String info = bufferedReader.readLine();
            if(info!=null){
                System.out.println("【服务端:】读取客户端信息:"+info);
            }

            //回复消息
            OutputStream outputStream = socket.getOutputStream();
            PrintWriter printWriter = new PrintWriter(outputStream);
            printWriter.print("【服务端:】我是服务端!你好呀!");
            printWriter.flush();
            //关闭输出流
            socket.shutdownOutput();
            //按层关闭所有流
            printWriter.close();
            outputStream.close();
            bufferedReader.close();
            inputStreamReader.close();
            inputStream.close();
            socket.close();
            server.close();
        } catch (IOException e) {
//            e.printStackTrace();
        }
    }
}

客户端代码

public class Client {
    public static void main(String[] args){
        try {
            //创建一个客户端,目标服务器ip为127.0.0.1,目标端口号为8080
            Socket socket = new Socket("127.0.0.1",8080);
            //发送信息流
            OutputStream outputStream = socket.getOutputStream();
            PrintWriter printWriter = new PrintWriter(outputStream);
            printWriter.print("【客户端:】我是客户端!你好呀!!!");
            //将缓冲区的数据强制输出,用于清空缓冲区,若直接调用close()方法,则可能会丢失缓冲区的数据。所以通俗来讲它起到的是刷新的作用。
            //而且如果不flush,服务端其实接收不到这边的信息的。尴尬哦!
            printWriter.flush();
            //关闭输出流
            socket.shutdownOutput();
            //接收信息流
            InputStream inputStream = socket.getInputStream();
            InputStreamReader inputStreamReader = new InputStreamReader(inputStream);
            BufferedReader bufferedReader = new BufferedReader(inputStreamReader);

            String info = bufferedReader.readLine();
            if(info!=null){
                System.out.println("【客户端:】读取服务端消息:"+info);
            }
            //关闭所有流
            bufferedReader.close();
            inputStreamReader.close();
            inputStream.close();
            printWriter.close();
            outputStream.close();
            socket.close();
        } catch (IOException e) {
//            e.printStackTrace();
        }
    }
}

先启动服务端,再启动客户端。我们可以看到两者的输出信息:


客户端
服务端你

参考资料:
socket原理

上一篇 下一篇

猜你喜欢

热点阅读