Индексирование массива наборов данных происходит очень медленно с помощью набора инструментов статистики - PullRequest
2 голосов
/ 14 июля 2011

Почему индексация в массиве наборов данных такая медленная?Пик в функции набора данных показывает, что все столбцы набора данных хранятся в массиве ячеек.Однако индексация ячеек намного, намного быстрее, чем индексация наборов данных, которая просто индексируется в массив ячеек под капотом.Я предполагаю, что это связано с некоторыми издержками с MATLAB OOP.Любые идеи о том, как ускорить это?

%% Using R2011a, PCWIN64
feature accel off;  % turn off JIT

dat = (1:1e6)';
dat2 = repmat({'abc'}, 1e6, 1);
celldat = {dat dat2};
ds = dataset(dat, dat2);
N = 1e2;

tic;
for j = 1:N
    tmp = celldat{2};
end
toc;

tic;
for j = 1:N
    tmp2 = ds.dat2; % 2.778sec spent on line 262 of dataset.subsref
end
toc;

feature accel on;  % turn JIT back on
Elapsed time is 0.000165 seconds.
Elapsed time is 2.778995 seconds.

РЕДАКТИРОВАТЬ: Я обновил пример, чтобы больше походить на проблему, которую я вижу.Огромное количество времени тратится на строку 262 набора данных.subsref - "b = a.data {varIndex};".Это очень странно для меня, поскольку это просто разыменование ячейки.Мне интересно, есть ли трюк ООП, который позволит мне индексировать в «a.data» без странных накладных расходов.

EDIT2: Согласно предложению Эндрю, я представилэто как ошибка в MatWorks.Обновлюсь, если что-нибудь услышу от них.

EDIT3: Matlab ответил и сказал, что они знают о проблеме сейчас и исправят ее в следующем выпуске.Они отметили, что проблема специфична для клеточных массивов, и, по возможности, стараемся избегать их.

1 Ответ

3 голосов
/ 14 июля 2011

Да, вы, скорее всего, видите накладные расходы на вызовы методов ООП Matlab. Они дороги по сравнению с индексацией ячеек или вызовами методов в некоторых других языках. Ваши .513872 секунды / 1e4 ~ = 51 микросекунда на вызов, что является приблизительной стоимостью нескольких вызовов метода MCOS; они ~ 5-15 микросекунд каждая на машинах, которые я видел. Таким образом, это выглядит как издержки метода самого вызова subsref () и других методов и свойств, обращающихся к нему по очереди.

Подробнее и обсуждение см .: MATLAB OOP работает медленно или я что-то не так делаю?

Я не знаю способа сделать это быстрее, кроме структурирования вашего кода, чтобы минимизировать обращения к "ds.dat" или другим методам. Если возможно, при работе с набором данных один раз вызовите «ds.dat», сохраните его в локальной переменной и поработайте с ним, а затем вставьте его обратно в объект ds.

Предостережение: я не знаю, что делает "Accele Feature" или как это может повлиять на эти сроки.

Редактировать: я бросил его в профилировщик, как предложил Ричи. На моем R2009b примерно половина времени - это накладные расходы при вызове метода, а остальное в find (), strcmp () и других операциях внутри subsref; subsref не вызывает никаких других методов по очереди.

Редактировать 2: пересмотренный пример показывает гораздо более высокие сроки. Затраты на вызов метода не учитывают всего этого.

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