求助!c#如何进行内存映射操作大文本?
c#如何进行内存映射操作大文本?像UltraEdit那样? --------------------编程问答-------------------- Up --------------------编程问答-------------------- 用C++吧 --------------------编程问答-------------------- 用什么写代码也解决不了影射30G的大文本这样的情况应该使用文件流的方式在这个流上开一个合适的内存窗口来显示需要显示编辑的内容.. --------------------编程问答-------------------- 参考如下代码,这是颠倒一个文件的内容
using System.Runtime.InteropServices;--------------------编程问答-------------------- To zhiang75
[DllImport("kernel32.dll")]
public static extern IntPtr CreateFileMapping(IntPtr hFile,
IntPtr lpFileMappingAttributes, uint flProtect,
uint dwMaximumSizeHigh,
uint dwMaximumSizeLow, string lpName);
[DllImport("kernel32.dll")]
public static extern IntPtr MapViewOfFile(IntPtr hFileMappingObject, uint
dwDesiredAccess, uint dwFileOffsetHigh, uint dwFileOffsetLow,
IntPtr dwNumberOfBytesToMap);
[DllImport("kernel32.dll")]
public static extern bool UnmapViewOfFile(IntPtr lpBaseAddress);
[DllImport("kernel32.dll")]
public static extern bool CloseHandle(IntPtr hObject);
[DllImport("kernel32.dll")]
public static extern IntPtr CreateFile(string lpFileName,
int dwDesiredAccess, FileShare dwShareMode, IntPtr securityAttrs,
FileMode dwCreationDisposition, int dwFlagsAndAttributes, IntPtr hTemplateFile);
[DllImport("kernel32.dll")]
public static extern uint GetFileSize(IntPtr hFile, IntPtr lpFileSizeHigh);
public const int GENERIC_READ = -2147483648; //0x80000000
public const int GENERIC_WRITE = 0x40000000;
public const int GENERIC_EXECUTE = 0x20000000;
public const int GENERIC_ALL = 0x10000000;
public const int FILE_ATTRIBUTE_NORMAL = 0x80;
public const int FILE_FLAG_SEQUENTIAL_SCAN = 0x8000000;
public const int INVALID_HANDLE_VALUE = -1;
public const int PAGE_NOACCESS = 1;
public const int PAGE_READONLY = 2;
public const int PAGE_READWRITE = 4;
public const int FILE_MAP_COPY = 1;
public const int FILE_MAP_WRITE = 2;
public const int FILE_MAP_READ = 4;
private void button1_Click(object sender, EventArgs e)
{
IntPtr vFileHandle = CreateFile(@"c:\temp\temp.txt",
GENERIC_READ | GENERIC_WRITE, FileShare.Read | FileShare.Write,
IntPtr.Zero, FileMode.Open,
FILE_ATTRIBUTE_NORMAL | FILE_FLAG_SEQUENTIAL_SCAN, IntPtr.Zero);
if (INVALID_HANDLE_VALUE != (int)vFileHandle)
{
IntPtr vMappingHandle = CreateFileMapping(
vFileHandle, IntPtr.Zero, PAGE_READWRITE, 0, 0, "~MappingTemp");
if (vMappingHandle != IntPtr.Zero)
{
IntPtr vHead = MapViewOfFile(vMappingHandle,
FILE_MAP_COPY | FILE_MAP_READ | FILE_MAP_WRITE, 0, 0, IntPtr.Zero);
if (vHead != IntPtr.Zero)
{
uint vSize = GetFileSize(vFileHandle, IntPtr.Zero);
for (int i = 0; i <= vSize / 2; i++)
{
byte vTemp = Marshal.ReadByte((IntPtr)((int)vHead + i));
Marshal.WriteByte((IntPtr)((int)vHead + i),
Marshal.ReadByte((IntPtr)((int)vHead + vSize - i - 1)));
Marshal.WriteByte((IntPtr)((int)vHead + vSize - i - 1), vTemp);
}
UnmapViewOfFile(vHead);
}
CloseHandle(vMappingHandle);
}
CloseHandle(vFileHandle);
}
}
不需要30G,只需要1G就可以了。如何使用文件流,能给个例子吗?
To zjh222
是在以前工具上进行二次开发,所以只能用c#. --------------------编程问答-------------------- 我的目的就是要实现一个类似文本编辑器的功能,如果把文本全加载到内存中,由于文本太大,很耗资源,所以我想是否应该用内存映射,动态加载文本。请大家给点意见。 --------------------编程问答-------------------- 这个帖子不错.... 我正需要内存映射大文本的解决方案..
学习先, 谢谢 --------------------编程问答-------------------- To zswang
谢谢你的代码,我正在研究。有些疑问,如果使用内存映射读取文本,只能一个字节一个字节读取吗,如果我想直接取第10行到第20行,能否做到?谢谢。 --------------------编程问答-------------------- 进来学习一下
--------------------编程问答-------------------- 用什么写代码也解决不了影射30G的大文本
----------------------------
30G不算啥,64位能表示多少,內存映射就有多少.
c#如何进行内存映射操作大文本?
----------------------------
1.使用CreateFile打開文件,獲取文件句柄
2.再使用CreateFileMapping來進行映射,指定要映射的大小.
3.多次使用MapViewOfFile來創建映射視圖,並獲得一個內存指針(該指針可以和內存一樣進行操作),每次創建視圖的大小不可超過1G,通常應該更小.視圖處理完成後,可以使用FlushMapView來提交更改(不是必須),應該使用UnmapViewOfFile來取消視圖.
4.使用CloseHandle來關閉由CreateFileMapping打開的映射句柄.
另外,4樓 伴水 清洁工 看帖要回贴 仁兄的例子衹是一個簡單的應用,可以供參考,理論上可以處理4G以內的文件,但實際上大多情況下,處理1G的文件都很可能出錯.因為使用MapViewOfFile時是創建整個文件的視圖. --------------------编程问答-------------------- To boblaw 黑马王子
使用 MapViewOfFile 超过1G就容易出错,那为了保证程序的稳定性,应该如何做呢? --------------------编程问答-------------------- MapViewOfFile超过1G就容易出错
----------------------
分多次使用MapViewOfFile,每次創建文件的部分視圖
下面是API原型
LPVOID MapViewOfFile(
HANDLE hFileMappingObject,
DWORD dwDesiredAccess,
DWORD dwFileOffsetHigh,
DWORD dwFileOffsetLow,
SIZE_T dwNumberOfBytesToMap
);
dwNumberOfBytesToMap:表示要創建視圖的大小
dwFileOffsetHight和dwFileOffsetLow:表示開始創建視圖位置起點,一個是高32位,一個是低32位,具體請查詢MSDN.
如果你勉強能看懂delphi的話,也可以參考我之前delphi版寫的一個示例(可以處理16EB文件大小):
http://topic.csdn.net/u/20071017/11/0c4d1b35-f449-471a-931b-6fd3738bb49f.html --------------------编程问答-------------------- 学习 --------------------编程问答-------------------- 用什么写代码也解决不了影射30G的大文本
----------------------------
表达问题,应该是
用什么语言写代码也解决不了影射30G的大文本
----------------------------
--------------------编程问答-------------------- 自己顶,看有没有更好的意见。 --------------------编程问答-------------------- 自己顶,看还有没有更好的意见 --------------------编程问答-------------------- 读第几行只能通过计算有多少个0x13字符来判断,先定位再处理
如果是插入或删除就很麻烦,要移动整个内容
楼主要实现什么样的功能? --------------------编程问答-------------------- 要做的这部分功能是类似于UltraEdit的功能,就是将文本显示出来,软件用的是一个RichTextBox,但是如果RichTextBox中存放的文本超过几M的话,软件的相应速度就会比较慢。我现在的做法是先将整个文本存放在一个List<string>中,动态把List<string>中的文本放到RichTextBox中。
但是如果文本文本达到几百兆,将整个文件全部放到List<string>中,会占用大量的内存,所以我想找个更好的解决办法。 --------------------编程问答-------------------- 要做的这部分功能是类似于UltraEdit的功能,就是将文本显示出来,软件用的是一个RichTextBox,但是如果RichTextBox中存放的文本超过几M的话,软件的相应速度就会比较慢。我现在的做法是先将整个文本存放在一个List<string>中,动态把List<string>中的文本放到RichTextBox中。
但是如果文本文本达到几百兆,将整个文件全部放到List<string>中,会占用大量的内存,所以我想找个更好的解决办法。 --------------------编程问答-------------------- 要做的这部分功能是类似于UltraEdit的功能,就是将文本显示出来,软件用的是一个RichTextBox,但是如果RichTextBox中存放的文本超过几M的话,软件的相应速度就会比较慢。我现在的做法是先将整个文本存放在一个List<string>中,动态把List<string>中的文本放到RichTextBox中。
但是如果文本文本达到几百兆,将整个文件全部放到List<string>中,会占用大量的内存,所以我想找个更好的解决办法。 --------------------编程问答-------------------- 这是一个Log分析器,必须将行号和内容记录下来,有一些互动,需要跳转到相应的行号。 --------------------编程问答-------------------- Mark 学习 --------------------编程问答-------------------- 这是一个Log分析器,必须将行号和内容记录下来,有一些互动,需要跳转到相应的行号。 --------------------编程问答-------------------- 沉得好快 --------------------编程问答-------------------- 顶
补充:.NET技术 , C#