学习网络编程练习时遇到的几个比较奇怪的现象,记录一下

在Java的网络编程实践中,作者遇到两个奇怪的现象。一是使用`newString(data)`构造字符串时,文本显示出现问题,而`newString(data,0,data.length)`则正常。二是发送数据时,默认编码可能导致中文字符丢失,指定UTF-8编码后问题解决。尽管IDEA的默认编码是UTF-8,但在某些情况下仍需明确指定编码方式。
摘要由CSDN通过智能技术生成

在练习网络编程的时候发现几个比较奇怪的现象,记录一下

我先把代码放上来

package com.atguigu.exercise.receiveandsend;  
  
import java.io.FileWriter;  
import java.io.IOException;  
import java.io.UnsupportedEncodingException;  
import java.net.*;  
import java.util.Scanner;  
  
/**  
 * @Description:  
 * @Author: Gavin  
 * @Date: 4/6/2023 6:15 PM  
 * receive and send demo */public class ReceiveAndSend {  
    public static void main(String[] args) throws IOException {  
        // 先创建DatagramSocket  
        DatagramSocket socket = new DatagramSocket(9000);  
  
        // 再来创建一个writter流,用来把接收到的聊天记录输出到文件里面  
        FileWriter fw = new FileWriter("testIO/chatLog.txt", true);  
  
  
        // 创建接受的thread  
        new Thread(new Runnable() {  
            @Override  
            public void run() {  
                while (true) {  
                    byte[] arr = new byte[1024];  
                    DatagramPacket packet = new DatagramPacket(arr, arr.length);  
                    try {  
                        socket.receive(packet);  
                    } catch (IOException e) {  
                        throw new RuntimeException(e);  
                    }  
                    // 将接收到的packet转换成信息  
                    byte[] data = packet.getData();  
                    int length = packet.getLength();  
                    String message  = new String(data);
                    //message = new String(data,0,data.length);  
                    String receiveMessage = "接受到来自:" + packet.getAddress() + ":" + packet.getPort() + "的信息:" + message + "\n";  
                    // 读取信息  
                    try {  
                        fw.write(receiveMessage);  
                        fw.flush();  
                    } catch (IOException e) {  
                        throw new RuntimeException(e);  
                    }  
                    if (message.equals("886")) {  
                        break;  
                    }  
                }  
  
            }  
        }, "receiver").start();  
  
  
        Scanner input = new Scanner(System.in);  
        // System.out.print("请输入对方的IP地址:");  
        // String ip = input.next();        String ip = "192.168.20.77";  
        // System.out.print("请输入对方的端口:");  
        // int port = input.nextInt();        int port = 9090;  
        InetAddress byName = InetAddress.getByName(ip);  
  
  
        // 创建发送的thread  
        new Thread(new Runnable() {  
            @Override  
            public void run() {  
                while (true) {  
                    System.out.print("请输入你想发送的内容:");  
                    String message = input.next();  
                    // 将message转成二进制  
                    byte[] bytes = new byte[0];  
                    try {  
                        bytes = message.getBytes("UTF-8");
                        //bytes = message.getBytes();  
                    } catch (UnsupportedEncodingException e) {  
                        throw new RuntimeException(e);  
                    }  
  
                    // 创建1个packet  
                    DatagramPacket packet = new DatagramPacket(bytes, bytes.length, byName, port);  
                    try {  
                        socket.send(packet);  
                    } catch (IOException e) {  
                        throw new RuntimeException(e);  
                    }  
                    if (message.equals("886")) {  
                        break;  
                    }  
                }  
            }  
        }, "sender").start();  
    }  
}

第一个奇怪的地方

在receiver Thread里面
对于收到的数据进行编码时
Pasted image 20230406202319
使用new String(data) 构造方法,文本中显示效果如下

Pasted image 20230406202437
如果改用new String(data,0,data.length)这个构造方法,显示效果就没有问题
Pasted image 20230406202513

我做了一个测试

package com.atguigu.exercise;  
  
import java.io.FileWriter;  
import java.io.IOException;  
  
/**  
 * @Description:  
 * @Author: Gavin  
 * @Date: 4/6/2023 8:13 PM  
 */public class Test01 {  
    public static void main(String[] args) throws IOException {  
        String str = "这是一条测试语句";  
        //先解码  
        byte[] bytes = str.getBytes();  
  
        //再来编码  
        String s1 = new String(bytes);  
  
        //第二种编码方式  
        String s2 = new String(bytes,0,bytes.length);  
  
        System.out.println("s1 = "+s1);  
        System.out.println("s2 = "+s2);  
  
        FileWriter write = new FileWriter("testIO/testString.txt");  
        write.write("s1 = "+s1);  
        write.flush();  
  
        write.write("\ns2 = "+s2);  
        write.flush();  
    }  
}

在这个测试中,不管是控制台输出语句,还是直接输出到文件中,效果都是正常的

控制台输出效果:
Pasted image 20230406202613

文本中输出效果:
Pasted image 20230406202633

关于下面这两种构造方法,看不出来什么区别,下面的最终调用的也是上面的这个方法

public String(byte[] bytes, int offset, int length) {  
    this(bytes, offset, length, Charset.defaultCharset());  
}

public String(byte[] bytes) {  
    this(bytes, 0, bytes.length);  
}

第二个比较奇怪的地方

在sender Thread里面,对要发送的数据进行解码的时候
Pasted image 20230406202724

如果我使用这条语句
bytes = message.getBytes();
那么网络调试助手里面收到的消息,英文字符完全正常,中文字符出现丢字现象,还出现 ?

Pasted image 20230406202833

当时当我手动指定编码方式为UTF-8之后,异常现象消失
也就是改写成这个语句
bytes = message.getBytes(“UTF-8”);

但是我的IDEA里面字符相关的设置默认就是UTF-8,没有选择过其他编码方式

以上两个现象很奇怪,想不明白

这是我IDEA里面编码相关的设置,全部都是UTF-8

Pasted image 20230406203049

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值