CallMe_DD 2022-11-06 21:40 采纳率: 66.7%
浏览 26
已结题

在本地实现图片的传输时,socket异常关闭的问题

在本地实现图片的传输时,socket异常关闭的问题

服务端

public static void main(String[] args) throws IOException {
        // 1. 监听 8888 端口
        ServerSocket serverSocket = new ServerSocket(8888);
        System.out.println("8888端口监听中...");

        // 2. 获取 socket 对象
        Socket socket = serverSocket.accept();

        // 3. 获取写入到本地磁盘的输出流
        FileOutputStream fos = new FileOutputStream("src/DD的头像.jpg");

        // 4. 读取 socket 输入流并写入文件
        BufferedInputStream bis = new BufferedInputStream(socket.getInputStream());
        BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(socket.getOutputStream(), "utf8"));
        int readLen;
        byte[] buf = new byte[10];
        while ((readLen = bis.read(buf)) != -1) {
            fos.write(buf, 0, readLen);
        }
        System.out.println("文件写入成功。。。");
        // 5. 向客户端发送保存成功的消息
        bw.write("图片保存成功!!!");
        bw.close();

        // 关闭相关流
        fos.close();
        bis.close();
        socket.close();
        serverSocket.close();
    }

客户端

public static void main(String[] args) throws IOException {
        // 1. 获取连接到服务器的 socket
        Socket socket = new Socket(InetAddress.getLocalHost(), 8888);
        // 2. 获取磁盘文件的输入流
        String filePath = "D:/FileStudy/DD的头像.jpg";
        FileInputStream fis = new FileInputStream(filePath);
        // 3. 读取磁盘文件
        BufferedOutputStream bo = new BufferedOutputStream(socket.getOutputStream());
        int readLen;
        byte[] buf = new byte[10];
        while ((readLen = fis.read(buf)) != -1) {
            // 4. 读取的同时,写入到数据通道
            bo.write(buf, 0, readLen);
        }
        bo.flush(); // ==============================================
        socket.shutdownOutput();
        // 5. 接收服务端发送的消息
        BufferedReader br = new BufferedReader(new InputStreamReader(socket.getInputStream(), "utf8"));
        System.out.println("接收到服务端的消息:" + br.readLine());

        // 关闭相关流
        br.close();
        bo.close(); // ==============================================
        socket.close();
    }

其中有很多 "=" 的那两行有点疑问(客户端的15和23行)

  1. 如果注释 bo.flush(),那么最后的 bo.close() 会爆 socket closed 异常,这是为什么?
  2. 如果把 bo.flush() 和 bo.close() 都注释掉,传输的图片就会不完整,这又是为啥
  • 写回答

1条回答 默认 最新

  • 燕少༒江湖 2022-11-07 10:08
    关注

    1、注释掉bo.flush并不会影响bo.close,你这里报错的socket closed,应该socket连接的错误。
    2、bo.flush() 和 bo.close(),是因为缓冲流BufferedOutputStream有未完成写入的数据,导致接收到未完成接受,所以导致图片不完整;
    3、BufferedOutputStream流在调用close方法的时候,在close直接,会判断是否完成写入数据的,如果没有,会自动调用flush方法。

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论

报告相同问题?

问题事件

  • 系统已结题 11月30日
  • 已采纳回答 11月22日
  • 修改了问题 11月6日
  • 创建了问题 11月6日

悬赏问题

  • ¥15 爬取豆瓣电影相关处理
  • ¥15 手机淘宝抓清除消息接口
  • ¥15 C#无selenium
  • ¥15 LD衰减计算的结果过大
  • ¥15 用机器学习方法帮助保险公司预测哪些是欺诈行为
  • ¥15 计算300m以内的LD衰减
  • ¥15 数据爬取,python
  • ¥15 怎么看 cst中一个面的功率分布图,请说明详细步骤。类似下图
  • ¥15 为什么我的pycharm无法用pyqt6的QtWebEngine
  • ¥15 FOR循环语句显示查询超过300S错误怎么办