nlfilter, принимающий одинаковые значения дважды - PullRequest
1 голос
/ 17 апреля 2011

Я использовал nlfilter для моей тестовой функции следующим образом:

function funct
clear all;
clc;
I = rand(11,11);
ld = input('Enter the lag = ') % prompt for lag distance
A = nlfilter(I, [7 7], @dirvar);

% Subfunction
    function [h] = dirvar(I)
        c = (size(I)+1)/2
        EW = I(c(1),c(2):end)
        h = length(EW) - ld
    end
end

Функция работает нормально, но ожидается, что nlfilter прогрессирует элемент за элементом, но на первых двух итерациях значения EW будут одинаковыми 0.2089 0.4162 0.9398 0.1058. Но затем для всех итераций выбирается следующий элемент, для 3-го это 0.4162 0.9398 0.1058 0.1920, для 4-го это 0.9398 0.1058 0.1920 0.5201 и так далее. Почему это так?

Ответы [ 2 ]

1 голос
/ 17 апреля 2011

Это не о чем беспокоиться.Это происходит потому, что nlfilter необходимо оценить вашу функцию, чтобы знать, какой вывод создать.Таким образом, он использует feval один раз, прежде чем начать перемещаться по изображению.Вывод этого feval вызова - это то, что вы видите в первый раз.

Из nlfilter кода:

% Find out what output type to make.
rows = 0:(nhood(1)-1);
cols = 0:(nhood(2)-1);
b = mkconstarray(class(feval(fun,aa(1+rows,1+cols),params{:})), 0, size(a));

% Apply fun to each neighborhood of a
f = waitbar(0,'Applying neighborhood operation...');
for i=1:ma,
    for j=1:na,
        x = aa(i+rows,j+cols);
        b(i,j) = feval(fun,x,params{:});
    end
    waitbar(i/ma)
end

Вызов в 4-й строкеto eval - это то, что вы наблюдаете как первый вывод EW, но он не используется ни для чего, кроме как превращение матрицы b в правильный класс.Все правильные итерации выполняются в цикле для ниже.Это означает, что наблюдаемые вами «повторяющиеся» значения не влияют на вашу конечную матрицу вывода, и вам не о чем беспокоиться.

0 голосов
/ 17 апреля 2011

Надеюсь, вы знаете, что делает функция length?Он не дает вам евклидовой длины вектора, а дает наибольшее измерение вектора (так в вашем случае это должно быть 4).Если вы хотите евклидову длину (или 2-норму), используйте вместо нее функцию norm.Если ваш код работает правильно, вы можете использовать что-то вроде:

sz = size(I,2);
h = sz - (sz+1)/2 - ld;

В вашем примере это означает, что в зависимости от предоставленной задержки, результат должен быть постоянным.Также обратите внимание, что вам может потребоваться ставить точку с запятой после каждой строки в вашей подфункции и что использование clear all в качестве первой строки функции бесполезно, поскольку функция всегда будет выполняться в своем собственном рабочем пространстве (однако при этом будут очищены постоянные или глобальные переменные, но вы не используете их в своем коде).

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