美文网首页
VC FILE*使用内存文件方法

VC FILE*使用内存文件方法

作者: 叶迎宪 | 来源:发表于2023-04-26 19:59 被阅读0次

有一个第三方库,输入参数之一是文件名,会把输出的内容写到这个文件中。我的应用程序再从这个文件中读入内容。由于这个第三方库每次产生的输出都很大,有十几兆,连续调用会产生大量的磁盘io,拖累性能。有没有办法让这个输出文件只存在于内存中,避免产生磁盘io呢?

尝试一:使用命名管道
https://github.com/msys2/MINGW-packages/issues/5903

示例

    HANDLE hpipe;
    char pipename[MAX_PATH];

    snprintf(pipename, sizeof(pipename), "\\\\.\\pipe\\msys_example_");

    hpipe = CreateNamedPipeA(pipename, PIPE_ACCESS_INBOUND,
        PIPE_TYPE_BYTE | PIPE_READMODE_BYTE | PIPE_WAIT,
        1, 1024, 1024, 0, NULL);
    if (hpipe == INVALID_HANDLE_VALUE)
    {
        fprintf(stderr, "Failed to create named pipe\n");
        return 1;
    }


    {  // 模拟第三方库打开并写入文件
        FILE* fp;
        fp = fopen(pipename, "wb");
        fprintf(fp, "abcd");
        fclose(fp);
    }

    {
        char buf[16];
        DWORD nBytesRead;
        ReadFile(hpipe, buf, 16, &nBytesRead, NULL);
    }
     
    CloseHandle(hpipe);

不过要注意的是,往pipe调用fwrite写入数据,或者fclose的时候(之前fwrite的数据要flush)可能会卡住,如果接收端没有及时取走数据,导致pipe的buffer塞满。对于要写入大量数据的情况,需要对应用进行改造,pipe的写入和读取分开到两个线程上同时进行

类似的linux下的方案
https://www.ibm.com/docs/en/zos/2.3.0?topic=io-using-named-pipes

尝试二:使用内存临时文件
https://github.com/Snaipe/fmem/blob/b73b3d8b570c2f79df5a0b071efba392a82ddcd7/src/fmem-winapi-tmpfile.c

其中的难点是 CreateFile 时的 (dwDesiredAccess, dwShareMode) 会影响影响后续打开是否成功
https://learn.microsoft.com/en-us/windows/win32/fileio/creating-and-opening-files
特别是如果带上了 FILE_FLAG_DELETE_ON_CLOSE,则要求 dwShareMode 带上 FILE_SHARE_DELETE,后续的打开也都要带上 FILE_SHARE_DELETE。而fopen等c库函数,都是不带FILE_SHARE_DELETE的。

示例

    char path[MAX_PATH];
    char file[MAX_PATH];

    if (!GetTempPathA(sizeof(path), path))
        return NULL;
    if (!GetTempFileNameA(path, "test", 0, file))
        return NULL;

    HANDLE handle = INVALID_HANDLE_VALUE;
    handle = CreateFileA(file,
            FILE_GENERIC_READ,
            FILE_SHARE_WRITE | FILE_SHARE_READ,
            NULL,
            CREATE_ALWAYS,
            FILE_ATTRIBUTE_TEMPORARY,
            NULL);

    { // 模拟第三方库打开并写入文件
        FILE* fp;
        fp = fopen(file, "wb");
        fprintf(fp, "abcd");
        fclose(fp);
    }

    { 
        char buf[16];
        FILE* fp;
        fp = fopen(file, "rb");
        fread(buf, 1, 16, fp);
        fclose(fp);
    }

    CloseHandle(handle); DeleteFileA(file); 

相关文章

  • java的IO流

    java中的File的使用 java中File的基础使用 文件的几个常用方法创建文件句柄。File是java.io...

  • go 文件操作

    File 建立File内存地址 打开文件 写文件 读文件 删除文件 判断文件是否存在 file写文件 file读文...

  • 写文件

    写文件-write 方法 要写入文件,请使用 write 方法,该方法将字符串写入文件。 例如: file = o...

  • 2.1 File类

    File类 使用File类可以访问到磁盘中的目录和文件。使用的方法是,首先创建一个File对象,如 创建File对...

  • 使用JS实现前端图片压缩预览

    方法1 1.首选使用files来获取文件属性,使用URL.createObjectURL方法将file文件转换为一...

  • node.js常用内置模块--File System

    File System表示文件系统, fs为它的缩写。这里只简单使用常用的方法,更多的使用方法请参阅官网File ...

  • StoryBoard的简单应用

    SB加载到内存 创建home.storyboard文件、然后通过代码加载到内存中。 SB里的VC跳转 VC中间的跳...

  • Python获取文件信息

    文件读写 open()与file() open()方法使用python内建函数操作文件file()则是构建了一个f...

  • OkHttp缓存

    代码实现: //创建手机内存文件夹(Environment用来管理手机SDcard内存的) File file =...

  • java中如何判断file是否存在

    java中如何判断file是否存在 此示例显示如何使用File类的file.exists()方法检查文件的存在。 ...

网友评论

      本文标题:VC FILE*使用内存文件方法

      本文链接:https://www.haomeiwen.com/subject/lwumjdtx.html