【问题标题】:Accessing large file in Azure在 Azure 中访问大文件
【发布时间】:2021-05-28 01:25:42
【问题描述】:

我有一个 winforms 应用程序,用户在其中输入一些文本并尝试将其与以该输入开头的大文件(约 5GB)中的特定行(或行块)匹配。

这些行按字母顺序排序,因此我执行二进制搜索并在 log(n) 时间内识别特定行,而不使用任何内存。为了更方便地在文件中导航,所有行都具有相同的大小(用空格填充)。

        using (var file = File.Open(filePath, FileMode.Open, FileAccess.Read, FileShare.Read))
        {
            long left = 0;
            long right = fileLength / lineLength - 1;
            byte[] buffer = new byte[lineLength];
            bool found = false;

            while (left <= right)
            {
                var middle = left + (right - left) / 2;
                file.Position = middle * lineLength;
                int read = file.Read(buffer, 0, lineLength);
                string line = Encoding.UTF8.GetString(buffer, 0, read);
                if (line.StartsWith(term))
                {
                    found = true;
                    break;
                }
                else if (string.Compare(line, term) < 0)
                {
                    left = middle + 1;
                }
                else
                {
                    right = middle - 1;
                }
            }

            if (found)
            {
              ....

代码中唯一的'昂贵'操作是file.Position 在文件的不同部分之间跳转(总是在某行的开头),直到找到特定的行。但是每次搜索不能超过 20 次跳转(总行数的 log2)。 winforms版本非常快,因为文件和可执行文件在同一台机器上。

我想使用 azure 函数将此工具移至 azure。我想继续使用相同的FileStream 逻辑来访问文件。 我怀疑 blob 存储不一定在具有 azure 功能的同一台机器上,因此File.Read 可能是针对不同机器的一些(慢)http 调用,并使我的搜索速度慢了几个数量级。

我应该将大文件放在哪里,以便在请求到达后立即进行搜索? 文件可以在执行azure函数的同一台机器上吗?

更新

是否可以在我的天蓝色函数项目中包含文件(嵌入式资源)? 它的大小限制是多少?

【问题讨论】:

标签: c# azure winforms azure-functions azure-blob-storage


【解决方案1】:

对 blob(或其他云)存储的访问(读/写/...)通常作为 REST API(而不是操作系统/文件系统 API,FileStream.read() 将使用)实现。您可以通过使用一些噱头(例如 FUSE 或如果您正在处理“File Share”)安装 blob/云存储来模拟文件系统,但支持和性能将非常值得怀疑,因为它是模拟并调用幕后的 REST API。


可以使用 REST API 中的范围选项来实现二进制搜索(需要随机访问文件)来读取 blob。

  • 这是REST API(对于 ADLS Gen2,如果您使用 Gen1 或 Blob,请找到正确的)
  • 这里有一些关于如何read a byte range 从 blob 中的文件中取出的说明。

所有语言 SDK 都建立在这些 REST API 之上。可能是其中一个 C# SDK API 提供了一个包装器/参数来读取范围,因此您可以在代码中使用它。如果没有,那么您将不得不调用 REST API。

注意

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-02-27
    • 1970-01-01
    • 1970-01-01
    • 2021-11-19
    • 1970-01-01
    • 2021-09-07
    相关资源
    最近更新 更多