Visual Basic, .NET, ASP, VBScript
 

   
   
     

Форум - .NET

Страница: 1 | 2 | 3 |

 

  Вопрос: C# : Очень медленно работает код! Добавлено: 04.09.10 11:05  

Автор вопроса:  Лёха | Web-сайт: supersait16.ucoz.ru

Ответить

  Ответы Всего ответов: 41  

Номер ответа: 16
Автор ответа:
 EROS



Вопросов: 58
Ответов: 4255
 Профиль | | #16 Добавлено: 06.09.10 19:33
Хотя, должен предупредить.. что ошибка не тривиальная.. и найти ее, точнее понять в чем косяк, будет достаточно не просто..

Ответить

Номер ответа: 17
Автор ответа:
 Лёха



Вопросов: 20
Ответов: 79
 Web-сайт: supersait16.ucoz.ru
 Профиль | | #17
Добавлено: 06.09.10 19:35
Я сейчас сижу ищу,но пока ничего не нашёл!

Ответить

Номер ответа: 18
Автор ответа:
 EROS



Вопросов: 58
Ответов: 4255
 Профиль | | #18 Добавлено: 06.09.10 20:10
Ладно, все равно ты не найдешь этот косяк..
Фишка в том, что если бы ты был внимательней то ты бы заметил, что я сначала создаю копию а потом проверяю формат, а ты же проверяешь PixelFormat а потом создаешь копию и с ней работаешь. Так вот, дефолтный конструктор new Bitmap создает картинку в формате Format32bppArgb т.е. изначально с альфа-каналом, а исходная твоя картинка имеет формат Format24bppRgb В результате - ты определяешь что у тебя 3 байта на пиксел, но работаешь с картинкой у которой реально 4 байта на пиксел и, как следствие, в оригинальном массиве у тебя один набор байт а работаешь ты совершенно с другим.. и из за этого у тебя неверный размер массива и шаг приращения в цикле.

Ответить

Номер ответа: 19
Автор ответа:
 Лёха



Вопросов: 20
Ответов: 79
 Web-сайт: supersait16.ucoz.ru
 Профиль | | #19
Добавлено: 06.09.10 21:14
А в С# работать с указателями так же как и в C++?

Ответить

Номер ответа: 20
Автор ответа:
 EROS



Вопросов: 58
Ответов: 4255
 Профиль | | #20 Добавлено: 06.09.10 21:20
да, только надо использовать unsafe mode

Ответить

Номер ответа: 21
Автор ответа:
 EROS



Вопросов: 58
Ответов: 4255
 Профиль | | #21 Добавлено: 06.09.10 21:23
и, разумеется, надо включить эту опцию в компиляторе.. по дефолту она отключена

Ответить

Номер ответа: 22
Автор ответа:
 Лёха



Вопросов: 20
Ответов: 79
 Web-сайт: supersait16.ucoz.ru
 Профиль | | #22
Добавлено: 06.09.10 21:25
Я так понимаю будет ещё быстрее? Этим способом быстро ,но хочется ещё быстрее,так как кртинка 4000х3000 обрабатывается с задержкой,
а хочется чтоб обрабатывалась с такой же скоростью как 320х240.Это реально на C#?

Ответить

Номер ответа: 23
Автор ответа:
 Лёха



Вопросов: 20
Ответов: 79
 Web-сайт: supersait16.ucoz.ru
 Профиль | | #23
Добавлено: 06.09.10 21:38
Если использовать unsafe mode надо собирать мусор,а как его собирать(чёто слышал про класс GC) ?

Ответить

Номер ответа: 24
Автор ответа:
 EROS



Вопросов: 58
Ответов: 4255
 Профиль | | #24 Добавлено: 06.09.10 21:44
Это даже на С++ не реально.. выше головы все равно не прыгнешь.. 4000*3000*4 это уже сам по себе достаточно серьезный размер массива.. и даже тупо перебрать его в цикле ничего не делая потребует времени.. При таких размерах,скорее всего, используются другие методы обработки изображений и это наверняка не просто инкрементация определенных байт.. С указателями ты однозначно получишь прирост производительности, но это не будет так же как 320*240.
Кстати, как вариант, при использовании FW 4/0, эта задача просто шикарно бы вписалась в концепцию распаралеливания.. и вот там,раскидав задачу по ядрам, скорее всего тоже можно получить прирост производительности.
Неплохо было бы прогнать бенчмарка на этой задаче..

Ответить

Номер ответа: 25
Автор ответа:
 EROS



Вопросов: 58
Ответов: 4255
 Профиль | | #25 Добавлено: 06.09.10 21:45
Если использовать unsafe mode надо собирать мусор,а как его собирать(чёто слышал про класс GC) ?

В твоем случае не будет мусора.. ты не плодишь объекты и не убиваешь их.. ты тупо будешь править память на лету..

Ответить

Номер ответа: 26
Автор ответа:
 Лёха



Вопросов: 20
Ответов: 79
 Web-сайт: supersait16.ucoz.ru
 Профиль | | #26
Добавлено: 06.09.10 21:58
Что-нибудь слышал про IPP?

Ответить

Номер ответа: 27
Автор ответа:
 Лёха



Вопросов: 20
Ответов: 79
 Web-сайт: supersait16.ucoz.ru
 Профиль | | #27
Добавлено: 06.09.10 22:31
Можешь пожалуйста написать простенький примерчик,для unsafe mode - как работать с памятью на лету,я попробовал чёто написать но из этого получился полный бред(с указателями плохо знаком):
  1. public unsafe void CorrectLevel(CorrectionLevel Level, int Offset)
  2.         {
  3.             if ((Offset < -255) || (Offset > 255))
  4.                 throw new ArgumentException();
  5.             BitmapData BData = IMG.LockBits(new Rectangle(0, 0, IMG.Width, IMG.Height),
  6.                  ImageLockMode.ReadWrite, IMG.PixelFormat);
  7.             int* Pointer = (int*)BData.Scan0.ToPointer();
  8.             *Pointer += Convert.ToInt32(Level);
  9.             for (int i = Convert.ToInt32(Level); i < OriginBytes.Length; i += BytesInPixel)
  10.             {
  11.                 int Value = OriginBytes + Offset;
  12.                 if (Value > 255) Value = 255;
  13.                 if (Value < 0) Value = 0;
  14.                 Pointer = (int*)Value;
  15.                 *Pointer += BytesInPixel;
  16.             }
  17.             IMG.UnlockBits(BData);
  18.             PreviewBox.Image = IMG;
  19.         }

Ответить

Номер ответа: 28
Автор ответа:
 EROS



Вопросов: 58
Ответов: 4255
 Профиль | | #28 Добавлено: 06.09.10 23:59
Я не сторонник использования unsafe mode, поэтому попробуй такой вариант правки памяти. Тут я избавился от 2х кратного копирования куска памяти в массив и обратно при каждом чихе, но остаются еще потери на проверки выхода за границы массива. В любом случае это должно несколько ускорить производительность..
Вот мой вариант..
  1.  
  2.         public void SetLevel(Levels level, int offset)
  3.         {
  4.             if (offset < -255 || offset > 255) throw new ArgumentOutOfRangeException();
  5.             BitmapData bitmapData = Image.LockBits(new Rectangle(0, 0, Image.Width, Image.Height), ImageLockMode.ReadWrite, Image.PixelFormat);
  6.             IntPtr pointer = bitmapData.Scan0;
  7.             for (int i = (int)level; i < originBytes.Length; i += bytesInPixel)
  8.             {
  9.                 int value = originBytes + offset;
  10.                 if (value > 255) value = 255;
  11.                 if (value < 0) value = 0;
  12.                 Marshal.WriteByte(pointer, i, (byte)value);
  13.             }
  14.             Image.UnlockBits(bitmapData);
  15.             OnImageChanged();
  16.         }

Ответить

Номер ответа: 29
Автор ответа:
 EROS



Вопросов: 58
Ответов: 4255
 Профиль | | #29 Добавлено: 07.09.10 01:25
Ну и последний вариант, с unsafe и указателями.. Не знаю,вряд ли он даст существенный прирост быстродействия.. если и даст то незначительный.. имхо, предыдущий вариант самый оптимальный для С#
  1.  
  2.         public void SetLevel(Levels level, int offset)
  3.         {
  4.             if (offset < -255 || offset > 255) throw new ArgumentOutOfRangeException();
  5.             BitmapData bitmapData = Image.LockBits(new Rectangle(0, 0, Image.Width, Image.Height), ImageLockMode.ReadWrite, Image.PixelFormat);
  6.             unsafe
  7.             {
  8.                 byte* memBitmap = (byte*)bitmapData.Scan0.ToPointer();
  9.                 fixed (byte* memOrigin = originBytes)
  10.                 {
  11.                     for (int i = (int)level; i < originBytes.Length; i += bytesInPixel)
  12.                     {
  13.                         int value = memOrigin + offset;
  14.                         if (value > 255) value = 255;
  15.                         if (value < 0) value = 0;
  16.                         memBitmap = (byte)value;
  17.                     }
  18.                 }
  19.             }
  20.             Image.UnlockBits(bitmapData);
  21.             OnImageChanged();
  22.         }

Ответить

Номер ответа: 30
Автор ответа:
 EROS



Вопросов: 58
Ответов: 4255
 Профиль | | #30 Добавлено: 07.09.10 01:31
Как обычно форум схавал i в квадратных скобках (((

Ответить

Страница: 1 | 2 | 3 |

Поиск по форуму



© Copyright 2002-2011 VBNet.RU | Пишите нам