# How to increase a matrix?

I need to increase a matrix inside a function. But `append!` works for vectors but doesn’t work for matrices

``````arg1=[1 2;3 4];

julia> append!(arg1, [5,6])
ERROR: MethodError: no method matching append!(::Array{Int64,2}, ::Array{Int64,1})
Closest candidates are:
append!(::Array{#s58,1} where #s58, ::AbstractArray{T,1} where T) at array.jl:895
append!(::Array{T,1} where T, ::Any) at array.jl:902
``````

So I thought in this trick via `reshape` but no luck either

``````julia> arg2=reshape(append!((reshape(arg1,:)), [5,6]), (2,3))
2×3 Array{Int64,2}:
1  2  5
3  4  6

julia> arg1
2×2 Array{Int64,2}:
1  2
3  4
``````

So, even all those operations are inplace the input `arg1` was not modified. This happens apparently because `reshape` creates a new object that in spite sharing the same memory is different thing and is that new object that gets appended.

`Matrix` is fixed size. Consider storing a `Vector` and just reshape where it is used as a Matrix.

1 Like

What I’ve done in the past is simply:

``````function resize_matrix(A, rows, cols)
resized = similar(A, rows, cols)
resized[1:size(A, 1), 1:size(A, 2)] = A
return resized
end
``````

This is quite inefficient, so if you continuously resize the matrix, it’s more efficient to resize it by chunks at a time (e.g. double it in size whenever capacity is reached).

You could also use a `Vector{Vector{Int}}()` and use `append!`.

Thanks but it won’t work for me. I need that all occurs inside a function and that the argument is modified and not to create a new object for returning.

``````function foo(mat, args...)
if (some_condition_in_args)
increase!(mat)
end
end
``````

so that if I call `foo()` the matrix `mat` gets (or not) increased.
And I need it to be a matrix, not a vector.

Then I’m afraid you will have to rethink. As Kristoffer points out, `Matrix` is fixed in size, so what you’re asking for is not possible with the `Matrix` type. Perhaps you can create your own resizable `AbstractMatrix` type using any of the ideas suggested above.

1 Like

You can’t use reshape either, since that fixes the size forever. The correct solution is to define your own `resizeMatrix <:AbstractMatrix` that wraps an underlying `Vector` for storage.

Luckily, https://github.com/JuliaArrays/ElasticArrays.jl does exactly that.

OK, thanks. I’ll keep trying till I get it.

The underlying-Vector/ElasticArrays solution only works for resizing the last dimension, right? So I guess it wouldn’t work for what OP is trying to do here, unless also transposing the data:

``````arg1=[1 2;3 4]
append!(arg1, [5,6])
``````

I haven’t look at `ElasticArrays` yet but tried playing with the vector conversions. And I get this new bizarre behavior (the column being appended is a 5x1 col

``````		@show(arg1)
arg1 = reshape(arg1, :)
cmd = add_opt(cmd, 'E', d, [:E :error_bars],
(x="|x",y="|y",xy="|xy",X="|X",Y="|Y",asym="+a",cap="+w",pen="+p"), false, arg1)
@show(arg1)
reshape(arg1, (5, 3))
@show(arg1)
``````

but last reshape refuses to … reshape. Running the code that calls the above chunk

``````arg1 = [1.175 25.0; 2.175 32.0; 3.175 34.0; 4.175 20.0; 5.175 25.0]
arg1 = [1.175, 2.175, 3.175, 4.175, 5.175, 25.0, 32.0, 34.0, 20.0, 25.0, 2.0, 3.0, 4.0, 1.0, 2.0]
arg1 = [1.175, 2.175, 3.175, 4.175, 5.175, 25.0, 32.0, 34.0, 20.0, 25.0, 2.0, 3.0, 4.0, 1.0, 2.0]
``````

Is it related to @foobar_lv2 statement that reshape fixes the size forever?
(it didn’t, but it doesn’t work either)

You’re not assigning the last `reshape` to `arg1`.

1 Like

Ah, still assuming that reshape works on place and does keeps the input object.
Thanks, convoluted but it seems to be working now.