методы обработки изображений - прямое манипулирование целевым изображением или виртуализация? - PullRequest
2 голосов
/ 17 мая 2009

Мне нужно заново спроецировать серию изображений Ариэля, на которые есть ссылки в географической системе координат, в проекцию UTM. Я читал, что использование getPixel и setPixel может быть медленным - следует установить серию двухмерных массивов для промежуточного доступа и затем сбросить значения в целевое изображение, когда я закончу.

Обычно это обработка изображений выполняется профессионалами?

Ответы [ 4 ]

4 голосов
/ 17 мая 2009

Большая часть обработки изображений - это обнаружение признаков, сегментация сцены, поиск неисправностей, классификация и отслеживание ....

Возможно, вы захотите взглянуть на книгу:

  1. Обработка изображений на С (применима и для других языков)
  2. Обработка изображений - Принципы и применение

Который описывает множество быстрых и эффективных способов многих преобразований изображений. Эти две книги помогли мне, когда я обрабатывал изображения:)

Если я понимаю ваш вопрос ... Если вы перестраиваете или собираете много изображений, и у вас нет ориентации, а также положения, вы можете использовать эти алгоритмы для повторного выравнивания краев и общих характеристик. Если вы выполняете сшивание по положению, эти алгоритмы помогут повторно сэмплировать / изменить размеры изображений для более эффективной сборки. Есть также несколько библиотек с открытым исходным кодом для такого рода вещей. (Приходит на ум OpenCV)

edit : Если бы я заново проецировал большие изображения в новые проекции, основанные на преобразовании положения (и это было динамическое, а не статическое), я бы посмотрел на создание приложения по требованию, которое будет рефакторировать изображения, данные Требуемое разрешение и желаемое положение. Затем приложение может вытащить ближайшее разрешение относительных изображений окрестностей и предоставить результат с требуемым разрешением.

Надеюсь, без дополнительной информации это поможет!

редактировать 2 : Комментарий от ответа ниже: Зависит от изображений. Если они имеют фиксированный размер, то массив может быть хорошим. Если они различаются, то может быть лучше реализовать систему, которая обеспечивает получение / установку пикселей с использованием относительной выборки / усреднения для сопоставления изображений с разным разрешением?

Я не знаю все входы и выходы изображений, с которыми вы работаете, и того, что вы делаете, но часто абстрагирование от значения «пиксель» вместо доступа к значениям в массиве полезно , Таким образом, вы можете реализовать преобразование, выборку, вращение, коррекцию алгоритмов на бэкэнде. Как GetVPixel () или SetVPixel (). Это может быть более полезно при работе с несколькими, разными изображениями в формате res / format. Как

SetVPixel(img1, coord1, GetVPixel(img2, coord2))

Очевидно, в форме ООП / С #. img1 и img2 могут различаться по размеру, размеру, географическому расположению, выравниванию или чему-либо еще, если ваш бэкэнд понимает оба.

3 голосов
/ 17 мая 2009

Если вы не возражаете против использования небезопасного кода, вы можете обернуть BitmapData растрового изображения в объект, который позволяет эффективно получать и устанавливать пиксели. Приведенный ниже код в основном взят из фильтра размытия по Гауссу с несколькими моими модификациями. Это не самый гибкий код, если ваши форматы растровых изображений отличаются, но я надеюсь, что он иллюстрирует, как вы можете более эффективно управлять растровыми изображениями.

public unsafe class RawBitmap : IDisposable
{
    private BitmapData _bitmapData;
    private byte* _begin;

    public RawBitmap(Bitmap originBitmap)
    {
        OriginBitmap = originBitmap;
        _bitmapData = OriginBitmap.LockBits(new Rectangle(0, 0, OriginBitmap.Width, OriginBitmap.Height), ImageLockMode.ReadWrite, PixelFormat.Format24bppRgb);
        _begin = (byte*)(void*)_bitmapData.Scan0;
    }

    #region IDisposable Members

    public void Dispose()
    {
        OriginBitmap.UnlockBits(_bitmapData);
    }

    #endregion

    public unsafe byte* Begin
    {
        get { return _begin; }
    }

    public unsafe byte* this[int x, int y]
    {
        get
        {
            return _begin + y * (_bitmapData.Stride) + x * 3;
        }
    }

    public unsafe byte* this[int x, int y, int offset]
    {
        get
        {
            return _begin + y * (_bitmapData.Stride) + x * 3 + offset;
        }
    }

    public unsafe void SetColor(int x, int y, Color color)
    {
        byte* p = this[x, y];
        p[0] = color.B;
        p[1] = color.G;
        p[2] = color.R;
    }

    public unsafe Color GetColor(int x, int y)
    {
        byte* p = this[x, y];

        return new Color
        (
            p[2],
            p[1],
            p[0]
        );
    }

    public int Stride
    {
        get { return _bitmapData.Stride; }
    }

    public int Width
    {
        get { return _bitmapData.Width; }
    }

    public int Height
    {
        get { return _bitmapData.Height; }
    }

    public int GetOffset()
    {
        return _bitmapData.Stride - _bitmapData.Width * 3;
    }

    public Bitmap OriginBitmap { get; private set; }
}
2 голосов
/ 17 мая 2009

Библиотека FreeImage довольно быстрая и предлагает вырезание и вставку, которые могут быть полезны. Дистрибутив поставляется с оболочкой C #.

1 голос
/ 17 мая 2009

AFAIK издержки GetPixel / SetPixel - это вызов к нему, при обращении к массиву нет вызова, следовательно, меньше служебных данных

Вы должны начать с GetPixel / SetPixel, вы всегда можете переопределить эти вызовы позже, чтобы использовать прямой доступ к данным.

...