I'm trying to reshape a long vertical image array (multidimensional RGB array) into layered horizontal sections in Octave.
I have a very long vertical image array (32734x1x3). How can I reshape the image array so I turn the long vertical image into a layered horizontal image array of 52x640x3 while the rest of the array is filled in with 0's to make it "square-ish"
I was looking at reshape
but couldn't figure out how to reshape an array in multiple dimensions while also creating the layered horizontal sections.
Simple Example: What space is left over in the array is filled in with zero's.
My logic/test was:
a=[1:32734]';
num_cols_wanted=640
num_of_rows_calc=ceil(size(a,1)/num_cols_wanted) %use ceil to get whole number rounded up
num_cells_to_add=mod(size(a,1),num_cols_wanted) %extra cells needed to even array out
b = zeros(num_of_rows_calc, num_cols_wanted); %preallocate
b=reshape(a,[num_of_rows_calc,num_cols_wanted]); %place reshaped a array into preallocated b array
At the end of the test script I'm having issues reshaping the original array a
into the larger preallocated array b
. I get an error can't reshape 32734x1
PS: I'm using Octave 5.2
When using reshape
, the number of input elements must be equal to the number of the output (reshaped) elements.
In your case: length(a)
must be equal to num_of_rows_calc*num_cols_wanted
.
Executing b = zeros(
...)
and then b = reshape(
...)
just overwrites the value of b
(filling b
with zeros doesn't help).
You may fill b
with zeros (create a "long" vector), and copy a
elements to the beginning of a
:
b = zeros(num_of_rows_calc*num_cols_wanted, 1);
b(1:length(a)) = a;
After having b
with correct number of element, we can reshape b
:
b = reshape(b, [num_cols_wanted, num_of_rows_calc])';
Note:
reshaping a vector in OCTAVE orders the elements by columns (top to bottom) first.
For ordering by rows, we may reshape to cols x rows and transpose the result.
Complete code sample:
%a=[1:32734]';
a = (1:10)';
num_cols_wanted=3; %640;
num_of_rows_calc=ceil(size(a,1)/num_cols_wanted); %use ceil to get whole number rounded up
num_cells_to_add=mod(size(a,1),num_cols_wanted); %extra cells needed to even array out
b = zeros(num_of_rows_calc*num_cols_wanted, 1); %Create a vector of zeros with desired number of elements.
b(1:length(a)) = a; %Copy a into the b - keeping the zeros at the end of b (we could also add zero padding at the end of a).
%Reshape to num_cols_wanted x num_of_rows_calc and transpose, because OCTAVE ordering is "column major".
b = reshape(b, [num_cols_wanted, num_of_rows_calc])'; %reshape b array into preallocated b array
Result:
b =
1 2 3
4 5 6
7 8 9
10 0 0
Example for 3D output:
a = cat(3, (1:10)', (21:30)', (31:40)');
a = squeeze(a); % Remove redunded dimentsion
num_cols_wanted=4;%640;
num_of_rows_calc=ceil(size(a,1)/num_cols_wanted); %use ceil to get whole number rounded up
num_cells_to_add=mod(size(a,1),num_cols_wanted); %extra cells needed to even array out
b = zeros(num_of_rows_calc*num_cols_wanted, 3); %Create 3 columns matrix of zeros with desired number of elements.
b(1:length(a), :) = a; %Copy a into the b - keeping the zeros at the end of b (we could also add zero padding at the end of a).
%Reshape to 3 x num_cols_wanted x num_of_rows_calc and permute, because OCTAVE ordering is "column major".
b = reshape(b, [num_cols_wanted, num_of_rows_calc, 3]); %reshape b array into preallocated b array
b = permute(b, [2, 1, 3]);