【问题标题】:RandomAccessFile reading Cyrillic UTF-8 javaRandomAccessFile 读取 Cyrillic UTF-8 java
【发布时间】:2013-10-27 23:27:50
【问题描述】:

伙计们!

我无法使用 RandomAccessFile 从文件中读取西里尔文文本。

这是一个简单的程序,它使用这种格式将信息写入特定文件(西里尔字母):

keyLength, valueLength, key, value

然后程序尝试读取此信息,但我的输出不正确:

writing success
keyLength = 10, valueLength = 4
read: килло, гр

UPD 预期输出:

writing success
keyLength = 10, valueLength = 4
read: киллограмм, сала

有什么问题? (除了我脑子小问题)

import java.io.FileNotFoundException;
import java.io.RandomAccessFile;
import java.io.IOException;

public class Main {

    public static void main(String[] args) {
        String fileName = "file.db";
        RandomAccessFile outputFile = null;

        try {
            outputFile = new RandomAccessFile(fileName, "rw");
        } catch (FileNotFoundException e) {
            System.err.println(e.getMessage());
            System.exit(1);
        }

        String key = "киллограмм";
        String value = "сала";

        try {
            outputFile.writeInt(key.length());
            outputFile.writeInt(value.length());

            outputFile.write(key.getBytes("UTF-8"));
            outputFile.write(value.getBytes("UTF-8"));
        } catch (IOException e) {
            System.err.println(e.getMessage());
            System.exit(1);
        }

        System.out.println("writing success");

        RandomAccessFile inputFile = null;

        try {
            inputFile = new RandomAccessFile(fileName, "r");
        } catch (FileNotFoundException e) {
            System.err.println(e.getMessage());
            System.exit(1);
        }

        int keyLength = 0, valueLength = 0;

        try {
            keyLength = inputFile.readInt();
            valueLength = inputFile.readInt();
        } catch (IOException e) {
            System.err.println(e.getMessage());
        }

        System.out.println("keyLength = " + keyLength + ", valueLength = " + valueLength);
        if (keyLength <= 0 || valueLength <= 0) {
            System.err.println("key or value length is negative");
            System.exit(1);
        }

        byte[] keyBytes = null, valueBytes = null;

        try {
            keyBytes = new byte[keyLength];
            valueBytes = new byte[valueLength];
        } catch (OutOfMemoryError e) {
            System.err.println(e.getMessage());
            System.exit(1);
        }

        try {
            inputFile.read(keyBytes);
            inputFile.read(valueBytes);
        } catch (IOException e) {
            System.err.println(e.getMessage());
            System.exit(1);
        }

        try {
            System.out.println("read: " + new String(keyBytes, "UTF-8") + ", " + new String(valueBytes, "UTF-8"));
        } catch (IOException e) {
            System.err.println(e.getMessage());
            System.exit(1);
        }

    }
}

【问题讨论】:

  • 你的预期输出是什么?
  • @SotiriosDelimanolis,更新
  • 如果您按顺序读取/写入,java.io.WriterReader 将包装一个 OutputStream/InputStream 并为您处理 UTF-8 或其他字符编码。您确定这些不是更好的解决方案吗?

标签: java utf-8 randomaccessfile cyrillic


【解决方案1】:

问题是这样的

outputFile.writeInt(key.length());

String#length()

返回此字符串的长度。长度等于数字 字符串中的 Unicode 代码单元。

在这种情况下,它返回值10,这不是表示此字符串所需的字节数。

你想要的是

key.getBytes("UTF-8").length

用作

byte[] keyBytes = key.getBytes("UTF-8");
outputFile.writeInt(keyBytes.length);

value 也是如此。

【讨论】:

  • @NinjaTurtle 另外,你有很多 try-catch 块。你为什么不把你所有的代码打包在一个块中呢?无论如何,你总是退出应用程序。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-06-21
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多