Недостаточно памяти с использованием bsxfun MATLAB

Я пытаюсь реализовать сжатие изображений с помощью преобразования Берроуза-Уилера. Рассмотрим одномерную матрицу сканирования пути:

p = [2 5 4 2 3 1 5];

а затем применить преобразование Берроуза-Уилера:

function output = bwtenc(p) 
n = numel(p);
x = zeros(length(p),1);
for i = 1:length(p)
    left_cyclic = mod(bsxfun(@plus, 1:n, (0:n-1).')-1, n) + 1;
    x = p(left_cyclic);
end
[lex ind] = sortrows(x);
output = lex(:,end);
output = uint8(output(:)');
end

И это работает! Но проблема в том, что когда я пытаюсь реализовать 1D-матрицу из Lena.bmp размером 512 * 512, появляется сообщение об ошибке, показывающее, что bsxfun не хватает памяти. Кто-нибудь, пожалуйста, помогите мне.


person yudha25    schedule 15.09.2014    source источник
comment
Нужна ли петля? x, кажется, принимает одинаковые значения во всех итерациях   -  person Luis Mendo    schedule 16.09.2014
comment
Спасибо за вашу доработку. Я уже удалил петлю, но все та же проблема. Сообщение об ошибке: ошибка при использовании bsx fun, недостаточно памяти. Пожалуйста помоги   -  person yudha25    schedule 16.09.2014
comment
Конечно, проблема с памятью была не из-за цикла. bsxfun пытается создать квадратную матрицу 512^2 x 512^2; Это проблема   -  person Luis Mendo    schedule 16.09.2014
comment
Какие могут быть проблемы с созданием матрицы 512x512? На какой конфигурации системы вы находитесь? Каков размер p?   -  person Divakar    schedule 16.09.2014
comment
Так у тебя есть какие-нибудь предложения для меня? Я использую bsxfun для левой циклической перестановки. Может быть у вас есть какой-нибудь код, чтобы заменить его? Я очень ценю вашу помощь   -  person yudha25    schedule 16.09.2014
comment
Размер p равен 1 размерной матрице из 512*512 = 1*262144. Я не знаю, почему появилось это сообщение об ошибке. У вас есть какие-нибудь предложения для меня?   -  person yudha25    schedule 16.09.2014
comment
@LuisMendo не могли бы вы мне помочь?   -  person yudha25    schedule 16.09.2014
comment
@ yudha25 Извините, я бы хотел, но не понимаю, как это сделать. Если я правильно понимаю, ваш p равен 512 ^ 2 x 1, поэтому left_cyclic (или x) равен 512 ^ 2 x 512 ^ 2. Это большая матрица. Я не вижу, как избежать его создания, так как вам нужно отсортировать его строки   -  person Luis Mendo    schedule 16.09.2014


Ответы (1)


Посмотрите, работает ли это для вас -

function output = bwtenc(p) 
np = numel(p);
[~,sorted_ind] = sort(p);
ind1 = mod((1:np)+np-2,np)+1;
output = p(ind1(sorted_ind));
output = uint8(output(:)');
end
person Divakar    schedule 15.09.2014
comment
Я очень ценю вашу помощь @Divakar. Но это не я хочу. Я хочу, чтобы результат был - person yudha25; 16.09.2014
comment
@ yudha25 Когда я использую p = [2 5 4 2 3 1 5] в качестве входных данных для вашего кода, я получаю вместо этого [3 4 5 2 5 1 2]. Итак, сначала исправьте свой код? - person Divakar; 16.09.2014
comment
@ yudha25 Вы хотите получить результат - p(left_cyclic), т.е. p(mod(bsxfun(@plus, 1:n, (0:n-1).')-1, n) + 1). Если ваш p ​​равен 1*262144, вы все равно хотите получить результат 262144x262144. Итак, вы ДОЛЖНЫ выйти из ошибки памяти! Но в любом случае вывод вашей функции не совпадает с тем, что вы только что сказали в качестве ожидаемого вывода в комментарии выше. Не могли бы вы прояснить все эти вопросы? - person Divakar; 16.09.2014
comment
Это проблема. Как я могу избежать этой ошибки памяти? - person yudha25; 16.09.2014
comment
@ yudha25 Если вы попытаетесь налить 2 литра воды в литровую чашку, вы ничего не сможете с этим сделать. Имеет смысл сейчас? В моей системе я не могу хранить 262144 x 262144 данные, поэтому на вашем месте я бы выбрал кластер MATLAB (если у меня есть доступ к кластеру) или просто попробовал какой-нибудь другой язык. - person Divakar; 16.09.2014
comment
Теперь я понимаю. Но если мы разделим 1*262144 на маленькие матрицы и напишем этот код, смогу ли я? - person yudha25; 16.09.2014
comment
@ yudha25 Ранее я задавал вам один вопрос - "When I use p = [2 5 4 2 3 1 5] as input to your code, I get this - [3 4 5 2 5 1 2] instead. So, correct your code first?", который был в ответ на ваш комментарий о том, что вывод должен быть выводом должен быть - p = [2 5 4 2 3 1 5; 5 4 2 3 1 5 2; 4 2 3 1 5 2 5; 2 3 1 5 2 5 4; 3 1 5 2 5 4 2; 1 5 2 5 4 2 3; 5 2 5 4 2 3 1]. Объясните это сначала. - person Divakar; 16.09.2014
comment
Мой ответ выше - это результат левой циклической перестановки. И, наконец, я беру последний столбец этого левого циклического результата @Divakar - person yudha25; 16.09.2014
comment
@ yudha25 Хорошо, при внимательном рассмотрении кажется, что из-за sortrows вы ДОЛЖНЫ обрабатывать все эти данные 262144 x 262144 одновременно, что означает, что ваша задача невозможна с существующей единой системой MATLAB. Либо используйте кластер MATLAB, либо используйте другую программную платформу/язык, либо ищите другой алгоритм для уменьшения размера данных. - person Divakar; 17.09.2014