如何使用MemoryMappedViewAccessor写入JSON序列化字符串到文件?
解决MemoryMappedViewAccessor写入JSON字符串的问题
嘿,我看到你在尝试用MemoryMappedFile写入JSON字符串时碰到了编译错误——确实,MemoryMappedViewAccessor的Write方法没有直接接收字符串的重载,因为内存映射文件本质上是操作原始字节数据的。不过别担心,只要把字符串转换成字节数组就能搞定,下面是具体的解决思路和修改后的代码:
核心思路
内存映射文件只能直接处理字节,所以我们需要做两步转换:
- 把JSON字符串通过指定编码(比如UTF-8)转换成字节数组
- 将字节数组写入内存映射文件,同时建议先写入字节数组的长度,方便后续读取时准确获取内容
修改后的WriteToFile方法
我帮你调整了WriteToFile方法,解决了编译问题,同时补充了资源释放和安全检查:
public void WriteToFile(string status) { Root root = new Root(); root.AllApplications.Add(new DataToWrite() { AppName = "DevOrca", Status = status }); var jsonString = JsonConvert.SerializeObject(root); // 1. 将JSON字符串转为UTF-8字节数组(注意读取时要使用相同编码) byte[] jsonBytes = Encoding.UTF8.GetBytes(jsonString); // 检查内容长度是否超过内存映射文件的容量(你创建时设的是1MB) if (jsonBytes.Length > 1024 * 1024) { throw new InvalidOperationException("JSON内容长度超过内存映射文件的最大容量,请调整文件大小"); } var accessor = AppViewModel.GetAccessor(); if (accessor == null) { throw new InvalidOperationException("内存映射视图访问器未初始化,请检查文件创建逻辑"); } try { mutex.WaitOne(); // 2. 先写入字节数组的长度(占用前4个int字节),方便后续读取时知道要读多少内容 accessor.Write(0, jsonBytes.Length); // 3. 从第4个字节开始写入JSON的字节内容 accessor.WriteArray(4, jsonBytes, 0, jsonBytes.Length); } finally { // 务必释放Mutex,避免死锁 mutex.ReleaseMutex(); // 释放访问器资源,防止内存泄漏 accessor.Dispose(); } }
额外补充:读取JSON的方法(如果需要)
如果你之后需要从内存映射文件读取JSON,同样要按字节数组读取再转成字符串,这里给你一个参考实现:
public string ReadJsonFromMemoryMap() { var accessor = AppViewModel.GetAccessor(); if (accessor == null) { return string.Empty; } try { mutex.WaitOne(); // 先读取之前写入的字节数组长度 int contentLength = accessor.ReadInt32(0); // 校验长度是否合法 if (contentLength <= 0 || contentLength > 1024 * 1024) { return string.Empty; } byte[] jsonBytes = new byte[contentLength]; // 从第4个字节开始读取对应长度的内容 accessor.ReadArray(4, jsonBytes, 0, contentLength); // 将字节数组转回JSON字符串 return Encoding.UTF8.GetString(jsonBytes); } finally { mutex.ReleaseMutex(); accessor.Dispose(); } }
注意事项
- 编码一致性:写入和读取必须使用相同的编码(比如都是UTF-8),否则会出现乱码
- 资源释放:
MemoryMappedViewAccessor实现了IDisposable接口,一定要在使用完后调用Dispose()释放资源 - Mutex安全:始终在
finally块中释放Mutex,避免因异常导致其他进程/线程无法获取锁 - 空间预留:如果JSON内容可能超过1MB,建议在创建
MemoryMappedFile时设置更大的容量,或者动态调整文件大小
内容的提问来源于stack exchange,提问作者nikhil
相关产品推荐
相关产品推荐

