如何防止 MappedByteBuffer 在文件末尾写入空字符?
Posted
技术标签:
【中文标题】如何防止 MappedByteBuffer 在文件末尾写入空字符?【英文标题】:How to prevent MappedByteBuffer put from writing null characters at the end of file? 【发布时间】:2019-12-30 22:50:46 【问题描述】:我正在使用具有固定缓冲区大小的 Java 的 MappedByteBuffer 来写入文件,作为分配的一部分。它应该逐个字符地写入,因为缓冲区大小可以小于行长。但问题是它将文件末尾缓冲区的剩余位置写为空字符。如何删除那些空字符?
这是一个示例代码:
import java.io.IOException;
import java.io.RandomAccessFile;
import java.nio.MappedByteBuffer;
import java.nio.channels.FileChannel;
public class Main
public static void main(String[] args) throws IOException
int bufferSize = 20;
RandomAccessFile file = new RandomAccessFile("test.txt", "rw");
MappedByteBuffer buffer = file.getChannel().map(FileChannel.MapMode.READ_WRITE, 0, bufferSize);
for (char c : "Line1".toCharArray())
buffer.put((byte) c);
buffer.put((byte)'\n');
for (char c : "Line2".toCharArray())
buffer.put((byte) c);
这是输出(使用 Sublime Text utf-8 编码打开):
【问题讨论】:
你试过在getChannel()
返回的FileChannel
上使用truncate()
吗?
【参考方案1】:
正如 Progman 所指出的,截断将解决您看到的问题。我使用 TextWrangler 复制了您看到的内容并显示了隐藏字符,然后我使用以下代码重新编写了它,并且尾随的空值消失了。关键变化是跟踪实际写入的字节数,然后将文件截断为该长度。
int bufferSize = 20;
int bytesWritten = 0;
RandomAccessFile file = new RandomAccessFile("test.txt", "rw");
MappedByteBuffer buffer = file.getChannel().map(FileChannel.MapMode.READ_WRITE, 0, bufferSize);
for (char c: "Line1".toCharArray())
buffer.put((byte) c);
bytesWritten++;
buffer.put((byte)
'\n');
bytesWritten++;
for (char c: "Line2".toCharArray())
buffer.put((byte) c);
bytesWritten++;
buffer.force(); //make sure all is written before messing with truncating
file.getChannel().truncate(bytesWritten);
【讨论】:
我很确定bytesWritten
变量不是必需的,您可以改用buffer.position()
。
好电话。我用 file.getChannel().truncate(buffer.position()); 试过了它确实奏效了。
@JeremyKahan,我正在执行相同的步骤,但出现错误 - 无法在打开用户映射部分的文件上执行请求的操作。你能帮我解决这个问题吗?
@ShubhamPandey 该文件可能已经被其他东西打开了吗?见***.com/questions/1302698/…
感谢您回复@JeremyKahan,这里只有 2 个对象在做这项工作,第一个是 FileChannel,另一个是 MappedByteBuffer。由于我从 fileChannel.truncate() 收到错误,我认为由于 mappedByteBuffer 仍处于打开状态,因此 fileChannel.truncate() 正在引发该错误。但是没有关闭 mappedByteBuffer 的方法。如果我没有得到解决方案,我的最后一个选择是替换这些 java.nio 类并转换为普通的 java.io 类,因为我从几天以来一直在努力解决这个问题。以上是关于如何防止 MappedByteBuffer 在文件末尾写入空字符?的主要内容,如果未能解决你的问题,请参考以下文章