Параметры компилятора с плавающей запятой C ++ | предотвращение a / b -> a * (1 / b)

Я пишу числовое программное обеспечение в реальном времени на C ++, в настоящее время компилирую его с Visual-C ++ 2008. Теперь, используя «быструю» модель с плавающей запятой ( / fp: fast ), различные оптимизации, большинство из которых полезны в моем случае, но конкретно:

a/b -> a*(1/b) Division by multiplicative inverse

слишком численно нестабильна для многих моих расчетов.

(см .: Microsoft Visual C ++ Оптимизация с плавающей запятой )

Переключение на / fp: точный делает мое приложение более чем в два раза медленнее. Возможно ли либо оптимизировать оптимизатор (т.е. отключить эту конкретную оптимизацию), либо каким-то образом обойти его вручную?

- Фактический пример минимального кода: -

void test(float a, float b, float c,
    float &ret0, float &ret1) {
  ret0 = b/a;
  ret1 = c/a;
} 

У меня также есть M, X-Y-Y "маскирующая" матрица. Моя цель - установить для элементов (Xi, Yi, :) в D значение NaN, когда (Xi, Yi) в M равно false. Есть ли способ избежать ...

Предположим, у меня есть D, матрица данных X-Y-Y-Z-Z. У меня также есть M, X-Y-Y "маскирующая" матрица. Моя цель - установить для элементов (Xi, Yi, :) в D значение NaN, когда (Xi, Yi) в M. ложно.

Есть ли способ избежать этого в цикле? Я попытался использовать ind2sub , но это не удалось:

M = logical(round(rand(3,3))); % mask
D = randn(3,3,2); % data

% try getting x,y pairs of elements to be masked
[x,y] = ind2sub(size(M),find(M == 0));
D_masked = D;
D_masked(x,y,:) = NaN; % does not work!

% do it the old-fashioned way
D_masked = D;
for iX = 1:size(M,1)
    for iY = 1:size(M,2)
        if ~M(iX,iY), D_masked(iX,iY,:) = NaN; end
    end
end

Я подозреваю, что здесь упущено что-то очевидное. (:

13
задан gnovice 6 August 2010 в 04:47
поделиться

2 ответа

Вы можете сделать это, реплицировав вашу логическую маску M на третье измерение с помощью REPMAT так, чтобы она была того же размера, что и D. Затем проиндексируйте:

D_masked = D;
D_masked(repmat(~M,[1 1 size(D,3)])) = NaN;

Если тиражирование матрицы маски нежелательно, есть другая альтернатива. Сначала можно найти набор линейных индексов, для которых M равен 0, затем повторить этот набор size(D,3) раз, затем сдвинуть каждый набор индексов на величину, кратную numel(M), чтобы он индексировал другую часть D в третьем измерении. Я проиллюстрирую это здесь, используя BSXFUN:

D_masked = D;
index = bsxfun(@plus,find(~M),(0:(size(D,3)-1)).*numel(M));
D_masked(index) = NaN;
13
ответ дан 2 December 2019 в 01:09
поделиться

Мой Matlab немного устарел, но я думаю, что логическая индексация должна работать:

D_masked = D;
D_masked[ M ] = NaN;

(что, вероятно, можно объединить в один оператор с условным выражением в правой части ...)

-2
ответ дан 2 December 2019 в 01:09
поделиться
Другие вопросы по тегам:

Похожие вопросы: