Можно ли векторизовать этот фрагмент сценария Matlab дальше? - PullRequest
1 голос
/ 16 июля 2010

Итак, что я пытаюсь сделать с этим кодом, так это найти все пиксели в строке изображения, которые находятся ниже определенного порога. Проблема, однако, заключается в том, что этот код выполняется в двойном цикле for (да, я знаю :(), один раз для каждого пикселя, поэтому он очень медленный. Мне интересно, могу ли я что-нибудь еще сделать.

Несколько советов было бы замечательно, так как я довольно плохо знаком с оптимизацией MATLAB и знаю только основы (стараюсь не использовать циклы или многократно вызывать сценарии во внутренних функциях и т. Д.). Если это не сработает, мне, возможно, придется прибегнуть к файлам MEX, и это будет сложнее поддерживать для других исследователей в моей группе. Спасибо!

for y = 1:y_len
    for x = 1:x_len
        %//...do stuff to calc slope and offset for the line, 
                %//this can be vectorized pretty easily.

        yIndices = xIndices.*slope + offset;
        yIndices = round(yIndices);

        yIndices = yIndices + 1;
        xIndices = xIndices + 1;
        valid_points = (yIndices <= 308) & (yIndices > 0);

        %this line is bottle necking----------------------------------------
        valid_points = yIndices(valid_points)+(xIndices(valid_points)-1)*308;
        %-------------------------------------------------------------------

        valid_points = valid_points(phaseMask_R(valid_points));
        t_vals = abs(phase_R(valid_points)-currentPhase);
        point_vals = [XsR(valid_points);YsR(valid_points)] - 1;
        matchedPtsCoordsR = point_vals(:,(t_vals<phaseThreshold) |(abs(192-t_vals)<phaseThreshold));

        matchedIndex = size(matchedPtsCoordsR,2);
        if(matchedIndex ==0)
          continue
        end

        centersMinMaxR = zeros(1,matchedIndex);
        cmmIndexR = 1;
        for a = 1:matchedIndex;
          if(a==1)
            avgPosition = matchedPtsCoordsR(:,a);
            centersMinMaxR(1,1) =1;
          else
            currentPosition = matchedPtsCoordsR(:,a);


            %also very slow----------------------------------------------
            distance = sum(abs(currentPosition-avgPosition));
            %------------------------------------------------------------
            if(distance>4) % We are now likely in a different segment.
              centersMinMaxR(2,cmmIndexR) = a-1;
              cmmIndexR = cmmIndexR + 1;
              centersMinMaxR(1,cmmIndexR) = a;
            end
            avgPosition = matchedPtsCoordsR(:,a);
          end
        end

        centersMinMaxR(2,cmmIndexR) = a;
        centersR = round(sum(centersMinMaxR)/2);

        %//...do stuff with centersR
                    %//I end up concatenating all the centersR into a 
                    %//large vector arrray with the start and end of 
                    %//each segment.

1 Ответ

1 голос
/ 17 июля 2010

Во-первых, MatLab Profiler - ваш лучший друг, и я полагаю, вы знаете об этом, потому что знаете, что за линия горлышка бутылки.

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

m = magic(2);
slope = 5;

m =
     1     3
     4     2

m(1,:) * slope  =
     5    15

m(:,1) * slope =
     5
    20

Вместо использования зубчатых массивов используйте разреженные массивы. Matlab имеет встроенную поддержку для них:

Matlab Создать разреженный массив

Операции с разреженными матрицами Matlab

UPDATE

Что касается преимуществ использования разреженного или обычного массива: Разреженный или нормальный массив Matlab

Разреженные матрицы являются настоящим благом для человек, который использует действительно разреженный матрицы, но 25% ненулей это просто не достаточно "разреженный" для любой выгоды в большинство случаев.

Ищите больше обновлений, так как у меня больше времени для просмотра вашего кода: p

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...