Уменьшите количество копий одного и того же объекта в куче больших объектов.

Я пытаюсь загрузить байты большого файла (около 30 МБ) с HTTPWebRequest на какой-то сервер. Проблема в том, что поскольку размер байтов превышает 85000, он сохраняется в LargeObjectHeap(LOH). Проблема в том, что мой код создает как минимум 5 экземпляров одного и того же объекта в LOH, которые затем не удаляются из памяти даже после закрытия потока ответов. Ниже приведен фрагмент кода, который вызывает эту проблему. До этого блока кода в LOH был только один экземпляр файла.

using (IO.Stream requestStream = webReqest.GetRequestStream())
{
    List<byte> uploadData = new List<byte>();
    uploadData.AddRange(Encoding.UTF8.GetBytes(stringContainingHeaderInfo));
    uploadData.AddRange(bytesOfTheLargeFile);

    byte[] fileFullData = uploadData.ToArray();
    requestStream.Write(fileFullData, 0, fileFullData.Length);
    requestStream.Close();

    uploadData.Clear();
    uploadData = null;
    fileFullData = null;
    fileEntityBytes = null;

   using (WebResponse webResponse = webRequest.GetResponse())
   {
      //Do Something with the response
   }
 }

Есть ли способ дальнейшей оптимизации этого блока кода, чтобы в куче создавалось меньше копий.


person Piyush    schedule 16.05.2014    source источник
comment
Какой сервер? Это ИИС?   -  person Robert Harvey    schedule 16.05.2014
comment
Да, @RobertHarvey, я пытаюсь загрузить его на сайт SharePoint, который будет работать в IIS.   -  person Piyush    schedule 16.05.2014
comment
Поскольку вы уже работаете с потоками, почему бы вам просто не использовать потоки повсюду и небольшие буферы фиксированного размера, а не загружать все данные в byte[]?   -  person Damien_The_Unbeliever    schedule 16.05.2014
comment
Кроме того, нет смысла делать uploadData.Clear(); uploadData = null; fileFullData = null; fileEntityBytes = null;   -  person John Saunders    schedule 16.05.2014
comment
@JohnSaunders На самом деле, когда создавалось несколько копий, я пытался установить для переменных значение null, которое больше не требуется. Но да, вы правы, они не оказали никакого влияния.   -  person Piyush    schedule 16.05.2014
comment
Эй, @JohnSaunders просто хотел добавить, что установка объектов в значение null не имеет значения, но очистка коллекции List оказывает непосредственное влияние. Если в LOH было 5 объектов, очистка списка уменьшала число до 3. Поскольку получение ответа занимает много времени, нет необходимости сохранять значения в списке.   -  person Piyush    schedule 16.05.2014
comment
Спасибо @Damien_The_Unbeliever, который помог. Когда я напрямую записывал байты в requestStream, в LOH попадает только 2 экземпляра вместо 5. Один для исходного byte[] и другой, возможно, для requestStream.   -  person Piyush    schedule 16.05.2014
comment
@user2223043 user2223043 смысл в том, чтобы в LOH не было копий. Скопируйте байты небольшими порциями. В более поздних версиях фреймворка есть метод Stream.Copy, который делает это за вас. Другими словами, вам не нужно bytesOfTheLargeFile.   -  person phoog    schedule 16.05.2014
comment
@Damien_The_Unbeliever Это следует превратить в ответ.   -  person ClickRick    schedule 22.05.2014


Ответы (1)


Microsoft недавно представила LargeObjectHeapCompactionMode для GC в .NET 4.5.1. Пожалуйста, используйте следующую ссылку, которая может вам помочь: http://msdn.microsoft.com/en-us/library/system.runtime.gcsettings.режимуплотнениякучибольшихобъектов%28v=vs.110%29.aspx

person Kajal Sinha    schedule 22.05.2014
comment
Спасибо за информацию. Это, безусловно, полезное дополнение от Microsoft. Однако его следует использовать в крайнем случае. Даже Microsoft выпустила предупреждение о том, что «сжатие LOH может быть дорогостоящей операцией и должно использоваться только после серьезного анализа производительности, как для определения того, что фрагментация LOH является проблемой, так и для принятия решения о том, когда запрашивать сжатие». Так что лучше постараться избегать этого как можно чаще. Это то, о чем я просил здесь, чтобы уменьшить количество повторяющихся записей в LOH. Если в LOH меньше копий, то фрагментация не будет проблемой. - person Piyush; 24.05.2014