我的科特林代码将拉丁字母字符转换为二进制代码,但非拉丁字母字符(阿姆哈拉语、阿拉伯语等)无法转换

My Kotlin code converts Latin alphabet characters to binary code but non-Latin alphabet characters(Amharic, Arabic etc) can't convert

大家好,我的代码将拉丁字母字符转换为二进制,但当我尝试转换非拉丁字母字符时崩溃。你能帮我一下,让我的代码可以转换每个字母表吗?

fun strToBinary(str: String): String {
    val builder = StringBuilder()

    for (c in str.toCharArray()) {
        val toString = c.code.toString(2) // get char value in binary
        builder.append(String.format("%08d", Integer.parseInt(toString))) // we complete to have 8 digits
    }

    return builder.toString()
}

当我尝试使用非拉丁字符时,出现此异常。

Exception in thread "main" java.lang.NumberFormatException: For input string: "11000100011"
    at java.lang.NumberFormatException.forInputString(NumberFormatException.java:65)
    at java.lang.Integer.parseInt(Integer.java:583)
    at java.lang.Integer.parseInt(Integer.java:615)
    at BinaryKt.strToBinary(Binary.kt:6)
    at BinaryKt.main(Binary.kt:41)
    at BinaryKt.main(Binary.kt)

你错误地认为一个字符总是占用 1 个字节。这仅在使用 ASCII 时是正确的,但不太常见的字符每个字符可能需要多达 4 个字节。

我建议首先使用 UTF-8 将整个字符串编码为 ByteArray,然后逐字节转换:

fun strToBinary(str: String) = buildString {
    str.toByteArray().forEach {
        append(it.toUByte()
            .toString(2)
            .padStart(8, '0')
        )
    }
}

请注意,这种编码占用了 space 的日志。结果字符串至少比原始文本长 8 倍。您可以使用十六进制编码使其缩短 4 倍:

fun strToHex(str: String) = buildString {
    str.toByteArray().forEach {
        append(it.toUByte()
            .toString(16)
            .padStart(2, '0')
        )
    }
}

或者使用 base64 编码使其更短:

fun strToBase64(str: String) = Base64.getEncoder().encodeToString(str.toByteArray())

更新

要解码字符串,我们基本上需要反转所有步骤。例如,为了从二进制解码,我们需要将字符串分成 8 个字符的部分,将每个部分解码为单个字节,创建字节数组,然后使用 UTF-8:

解码为字符串
fun binaryToStr(binary: String) =
    binary.chunked(8)
        .map { it.toUByte(2).toByte() }
        .toByteArray()
        .decodeToString()