在 C# 中部分下载并序列化大文件?

2023-12-01

作为我大学即将进行的项目的一部分,我需要编写一个客户端,从服务器下载媒体文件并将其写入本地磁盘。由于这些文件可能非常大,我需要实现部分下载和序列化以避免过多的内存使用。

我想出了什么:

namespace PartialDownloadTester
{
    using System;
    using System.Diagnostics.Contracts;
    using System.IO;
    using System.Net;
    using System.Text;

    public class DownloadClient
    {
        public static void Main(string[] args)
        {
            var dlc = new DownloadClient(args[0], args[1], args[2]);
            dlc.DownloadAndSaveToDisk();
            Console.ReadLine();
        }

        private WebRequest request;

        // directory of file
        private string dir;

        // full file identifier
        private string filePath;

        public DownloadClient(string uri, string fileName, string fileType)
        {
            this.request = WebRequest.Create(uri);
            this.request.Method = "GET";
            var sb = new StringBuilder();
            sb.Append("C:\\testdata\\DownloadedData\\");
            this.dir = sb.ToString();
            sb.Append(fileName + "." + fileType);
            this.filePath = sb.ToString();
        }

        public void DownloadAndSaveToDisk()
        {
            // make sure directory exists
            this.CreateDir();

            var response = (HttpWebResponse)request.GetResponse();
            Console.WriteLine("Content length: " + response.ContentLength);
            var rStream = response.GetResponseStream();
            int bytesRead = -1;
            do
            {
                var buf = new byte[2048];
                bytesRead = rStream.Read(buf, 0, buf.Length);
                rStream.Flush();
                this.SerializeFileChunk(buf);
            }
            while (bytesRead != 0);
        }

        private void CreateDir()
        {
            if (!Directory.Exists(dir))
            {
                Directory.CreateDirectory(dir);
            }
        }

        private void SerializeFileChunk(byte[] bytes)
        {
            Contract.Requires(!Object.ReferenceEquals(bytes, null));
            FileStream fs = File.Open(filePath, FileMode.Append);
            fs.Write(bytes, 0, bytes.Length);
            fs.Flush();
            fs.Close();
        }
    }
}

出于测试目的,我使用了以下参数:

“http://itu.dk/people/janv/mufc_abc.jpg”“mufc_abc”“jpg”

然而,即使内容长度打印为 63780(图像的实际大小),图片也不完整(只有前 10% 看起来正确)。

所以我的问题是:

  1. 这是进行部分下载和序列化的正确方法还是有更好/更简单的方法?
  2. 响应流的全部内容是否存储在客户端内存中?如果是这种情况,我是否需要使用 HttpWebRequest.AddRange 从服务器部分下载数据以节省客户端内存?
  3. 为什么序列化失败并且图像损坏?
  4. 当我使用 FileMode.Append 时,是否会引入大量开销? (msdn 指出此选项“查找文件末尾”)

提前致谢


你绝对可以使用简化你的代码网络客户端:

class Program
{
    static void Main()
    {
        DownloadClient("http://itu.dk/people/janv/mufc_abc.jpg", "mufc_abc.jpg");
    }

    public static void DownloadClient(string uri, string fileName)
    {
        using (var client = new WebClient())
        {
            using (var stream = client.OpenRead(uri))
            {
                // work with chunks of 2KB => adjust if necessary
                const int chunkSize = 2048;
                var buffer = new byte[chunkSize];
                using (var output = File.OpenWrite(fileName))
                {
                    int bytesRead;
                    while ((bytesRead = stream.Read(buffer, 0, buffer.Length)) > 0)
                    {
                        output.Write(buffer, 0, bytesRead);
                    }
                }
            }
        }
    }
}

请注意,我如何仅将实际从套接字读取的字节数写入输出文件,而不是整个 2KB 缓冲区。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

在 C# 中部分下载并序列化大文件? 的相关文章

随机推荐

  • 分割逗号分隔的字符串,但忽略逗号后跟空格

    公共静态无效主 字符串 args String title Today and tomorrow 2 1 2 5 0 String titleSep title split System out println Arrays toStrin
  • 用户控件的数据上下文

    我正在创建一个UserControl我想用这样的东西
  • 如何防止在 boost::fast_pool_allocator 管理的对象上调用析构函数?

    我想利用以下广告功能boost fast pool allocator see Boost Pool 的 Boost 文档 例如 您可能会遇到这样的情况 您想要分配一个 一堆小物体在一个点上 然后到达你的一个点 不再需要它们的程序 使用池接
  • 了解 TensorBoard(权重)直方图

    在 TensorBoard 中查看和理解标量值非常简单 然而 目前尚不清楚如何理解直方图 例如 它们是我的网络权重的直方图 After fixing a bug thanks to sunside What is the best way
  • watch 命令不适用于使用管道的命令[关闭]

    Closed 这个问题是无法重现或由拼写错误引起 目前不接受答案 非常简单 快速的问题 为什么这个命令不起作用 watch ls log wc l or watch d ls log wc l 我正在尝试watch当前目录中文件总数的更新
  • 未能在 build.sbt 中包含 com.typesafe(对于 Scala 和 Heroku 上的 Spray)

    尝试引导我的 Scala 样板SprayHeroku 上的项目 我正在尝试按照以下方式向我的本地项目添加必要的调整Heroku 文档 喷雾样板项目源自github上的优秀模板它简单有效 并且包含优雅的代码和测试 在最后提到的模板项目运行良好
  • NVIDIA Parallel Nsight 与 Visual Profiler

    我正在Windows平台上使用CUDA 在 Windows 平台上 我们可以访问 Parallel Nsight 和 Visual Profiler 两者都非常好 但它们在分析和跟踪方面具有几乎相似的功能 有人能告诉我它们有什么不同吗 哪一
  • 强制标签文本从左到右,同时包含一些从右到左的文本

    我有一根绳子 代表货币符号 我从中得到NSLocale localeIdentifier ar AE objectForKey NSLocaleCurrencySymbol as String In my UILabel 当我将文本设置为t
  • SQL Server 模板 - 如何转义小于字符?

    我喜欢使用 SQL Server 2005 模板来运行常用查询 您可以使用以下语法在模板中包含参数
  • 是否可以使用 ColdFusion 重写 url?

    我需要生成用户友好的 url 我在 IIS 上 我的动态 URL 看起来像 www testsite com blog article cfm articleid 4432 客户希望网址看起来像 www testsite com blog
  • IE CSS Bug - 当页面上的动态 javascript 内容更改时如何保持位置:绝对

    我有一个页面 其中有一个列和一个内容 div 有点像这样 div div blahblahblah div div div div 通过一些样式 我有一个图像在列和内容之间分开 但需要保持相同的垂直位置 以便它对齐 样式类似于这样 colu
  • 背景图像隐藏了所有 GUI 设计组件

    我正在开发 GUI 应用程序 我使用 swing 组件来设计 GUI 我想为我的表单设置背景图像 但是当我设置图像时 它会重叠用于设计 GUI 的所有组件 首先我的没有背景图片的表格如下所示 我的代码是 登录 java public cla
  • 在 Magento 中将数组转换为集合

    我有一个数组对象 它是来自数据库的 magento fetchall 的输出 我希望将其转换为 Collections 类的对象 以便我可以实现分页并使用此集合与其他表连接 你能帮我一下吗 已经卡了好久了 要将数组转换为集合对象 1 gt
  • “System.IO.IOException:操作成功完成”异常

    我遇到了这个异常 System IO IOException 操作成功完成 在下面的代码块中 此代码在 Windows 服务中运行 foreach var error in currentPowerShell Streams Error i
  • 访问类的多处理代理的属性

    我有一个类 我想以只读方式与池中的子进程共享 因此我准备了一个类的代理 但它不起作用 以下是我的问题的简化示例 from multiprocessing managers import BaseManager class TestClass
  • 在这种情况下需要对 Node.js 中的函数进行阻塞调用吗?

    我开始学习node js 我在这里遇到了一个问题 我正在调用返回 JSON 的天气服务 网址如下 http api wunderground com api Your key conditions q CA San Francisco js
  • 用于 CGM 文件转换的 .NET 库

    我一直在开发一个实用程序 将各种文件转换为 PDF 以便于打印 通过电子邮件发送 我正在尝试添加对 CGM 文件的支持 但无法找到任何库来帮助我做到这一点 这是我可以在 C 中本地完成的事情吗 或者是否有任何基于 NET 的库可以帮助我转换
  • 如何判断是否支持window.confirm()?

    我有一个移动网站 可供各种设备使用 包括一些运行带有 IE 7 的 Windows Embedded 7 锁定版本的车载计算机 出于某种我无法解释的原因 window confirm 已损坏 但所有其他 javascript 似乎都可以工作
  • javascript/canvas,地图样式点缩放

    我有一张画布 上面有一堆物体 我有一个缩放功能 可以放大zoom每个坐标都乘以的变量 我希望能够指向一个坐标并对其进行缩放 类似于在线地图的操作方式 我已经设置了一个演示here 我的代码的当前状态 坐标处的比例 如果给定的屏幕坐标已缩放内
  • 在 C# 中部分下载并序列化大文件?

    作为我大学即将进行的项目的一部分 我需要编写一个客户端 从服务器下载媒体文件并将其写入本地磁盘 由于这些文件可能非常大 我需要实现部分下载和序列化以避免过多的内存使用 我想出了什么 namespace PartialDownloadTest