Это бит вашего кода, который я не понял:
a = (l2(m-M,n-M)+eps/l1(m-M,n-M)+l2(m-M,n-M)+2*eps)*M;
b = (l1(m-M,n-M)+eps/l1(m-M,n-M)+l2(m-M,n-M)+2*eps)*M;
Я упростил выражение для b
до (просто удалив индексирование):
b = (l1+eps/l1+l2+2*eps)*M;
Для l1
и l2
в нормальном диапазоне мы получаем:
b =(approx)= (l1+0/l1+l2+2*0)*M = (l1+l2)*M;
Таким образом, b
может легко быть больше, чем M
, что я не думаю,это твое намерение.eps
в этом случае также не защищает от деления на ноль, что обычно является целью добавления eps
: если l1
равно нулю, eps/l1
равно Inf
.
Lookingв этом выражении мне кажется, что вы намеревались это вместо этого:
b = (l1+eps)/(l1+l2+2*eps)*M;
Здесь вы добавляете eps
к каждому из собственных значений, делая их гарантированно ненулевыми (тензор структуры симметричен, положительный полуопределенный).Затем вы делите l1
на сумму собственных значений и умножаете на M
, что приводит к значению между 0
и M
для каждой из осей.
Итак, это кажетсячтобы быть случай неправильной скобки.
Просто для записи, это то, что вам нужно в вашем коде:
a = (l2(m-M,n-M)+eps ) / ( l1(m-M,n-M)+l2(m-M,n-M)+2*eps)*M;
b = (l1(m-M,n-M)+eps ) / ( l1(m-M,n-M)+l2(m-M,n-M)+2*eps)*M;
^ ^
added parentheses
Обратите внимание, что вы можете упростить свой код, определив,вне циклов:
[se_x,se_y] = meshgrid(-M:M,-M:M);
Внутренние два цикла, более i
и j
, для построения se
могут быть записаны просто как:
se = ((se_x.*cos(phi)+se_y.*sin(phi)).^2)./a.^2 + ...
((se_x.*sin(phi)-se_y.*cos(phi)).^2)./b.^2 <= 1;
(Обратите внимание на операторы .*
и .^
, которые выполняют поэлементное умножение и мощность.)
Еще одно небольшое улучшение происходит от понимания того, что phi
сначала вычисляется из e1(m,n,1)
и e1(m,n,2)
,а затем используется в вызовах на cos
и sin
.Если предположить, что собственный вектор правильно нормализован, то
cos(phi) == e1(m,n,1)
sin(phi) == e1(m,n,2)
Но вы всегда можете убедиться, что они нормализованы:
cos_phi = e1(m-M,n-M,1);
sin_phi = e1(m-M,n-M,2);
len = hypot(cos_phi,sin_phi);
cos_phi = cos_phi / len;
sin_phi = sin_phi / len;
se = ((se_x.*cos_phi+se_y.*sin_phi).^2)./a.^2 + ...
((se_x.*sin_phi-se_y.*cos_phi).^2)./b.^2 <= 1;
Учитывая, что тригонометрические операции довольно дороги, это должно ускоритьВаш код немного.