Вызов функции без цикла для векторных / матричных членов в Matlab / Octave - PullRequest
5 голосов
/ 18 марта 2010

Я пришел в мир матриц из мира петель (C и т. Д.)

Я хотел бы вызвать функцию для каждого отдельного члена вектора / матрицы и вернуть полученный вектор / матрицу.

Вот как я сейчас это делаю:

function retval = gauss(v, a, b, c)
  for i = 1:length(v)
    retval(i) = a*(e^(-(v(i)-b)*(v(i)-b)/(2*c*c)));
  endfor
endfunction

Пример использования:

octave:47> d=[1:1000];
octave:48> mycurve=gauss(d, 1, 500, 100);

Теперь все советы по MATLAB / Octave гласят: ОСТАНОВИТЕСЬ всякий раз, когда вы ловите себя на петлях, и придумайте лучший способ сделать это.

Таким образом, мой вопрос: Можно ли вызвать функцию для каждого члена вектора / матрицы и вернуть результат в новом векторе / матрице сразу, без использования явных циклов?

То есть я ищу что-то вроде этого:

 function retval = newfun(v)
    retval = 42*(v^23); 
endfunction

Возможно, это всего лишь синтаксический сахар, вот и все, но все же было бы полезно знать.

Ответы [ 4 ]

6 голосов
/ 18 марта 2010

В Matlab '.' Префикс на операторах является поэлементной операцией.

Попробуйте что-то вроде этого:

function r = newfun(v)
 r = a.*exp(-(v-b).^2./(2*c^2))
end
6 голосов
/ 18 марта 2010

Функция должна выглядеть следующим образом:

function retval = gauss(v, a, b, c)
  retval = a*exp(-(v-b).^2/(2*c^2));

Я бы порекомендовал вам прочитать документацию MATLAB о том, как векторизовать код и избежать циклов:

Руководство по векторизации кода

Методы повышения производительности

Также помните, что иногда код с циклами может быть более понятным, чем векторизованный, и с недавним представлением JIT-компилятора MATLAB работает с цикламидовольно хорошо.

3 голосов
/ 18 марта 2010

ARRAYFUN (и его родственники) - обычный способ сделать это.

Но в вашем конкретном случае вы можете просто сделать

mycurve = a*exp(-(d-b).^2/(2*c^2));

Это не просто синтаксический сахар; устранение циклов делает ваш код намного быстрее.

1 голос
/ 18 марта 2010

Да.

function retval = newfun(v)
    retval = a*exp(-((v-b).^2)/(2*c*c));
endfunction
...