-
-
Notifications
You must be signed in to change notification settings - Fork 14
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
istril
, istriu
, diag
, etc for block diagonal matrices
#610
Comments
The use case for block diagonal matrices are its application in solving Dirac Equation (https://en.wikipedia.org/wiki/Dirac_equation) and fast matrix multiplication using Strassen's Algorithm (I don't know if it's already implemented or not)
What exactly is missing? |
Yes. We should have gone through the methods in |
Oo! Apparently, even for general block matrices
The same is true for In this sense, we are introducing inconsistency when we look at band structure recursively. The big question seems to be whether this is just oversight in Also, it seems that symmetry/Hermitianness is determined somewhat recursively: we go through one triangle of the outer matrix, and ask whether that entry is equal to its own transpose/adjoint. This comparison, I guess, goes down the hierarchy if necessary. The following work as one would expect from a recursive/flattened viewpoint:
In summary, the issue is more general than described in the OP. |
I had a quick look at where If I understand that correctly, then (at least) in this case we really do want
is diagonal, and we would want that to be recognized when solving. Admittedly, |
I was surprised at first by the following behaviour: julia> A = Diagonal([[1 2], [3 4 5; 5 6 7; 8 9 10]])
2×2 Diagonal{Array{Int64,2},Array{Array{Int64,2},1}}:
[1 2] ⋅
⋅ [3 4 5; 5 6 7; 8 9 10]
julia> A[1,2]
1×3 Array{Int64,2}:
0 0 0
julia> A[2,1]
3×2 Array{Int64,2}:
0 0
0 0
0 0 But it ended up being very helpful for diagonal This is very similar to the discussion on whether |
@dlfivefifty So what's the conclusion? Do we judge symmetry, band/diagonal/triangular structure recursively/elementwise? Then the use of |
I have no conclusion, and am happy with whatever the consensus is. |
We continue to have the problem that no one has ever written down what a matrix of matrices is supposed to represent. Without such a statement, questions like "should |
This is slightly off the main topic but still relevant. To me, it doesn't seem like having block matrices in the stdlib is worth the trouble. This would be a breaking change but it seems like we should restrict all matrices in LinearAlgebra to those with numerical eltypes. One can use a third party package if they really need block matrix support (these exist already). As Stefan said we have an inconsistent (or non existent) definition and even simple stuff on block matrices fails in the current release. |
Restricting to That said, I think in the specific case of block-matrices I find linear algebra ill-defined without control on the block sizes, and better left to BlockArrays.jl. Though LinearAlgebra could still work with something like |
Yes, I noticed that consistency of block sizes is never checked. One case where block stuff works nicely is with block-diagonal matrices. Here, solve "passes" the |
In any case, the PR related to this issue is introducing the following inconsistency:
whereas the same matrix written as block-diagonal yields
with the PR. I'm not sure we really need a clear and universal definition of what block matrices are supposed to represent to improve consistency (although that would be generally appreciated, no doubt). Regardless of that definition, one may ask two different questions on block matrices: (i) is there block-band structure or not, and (ii) is there band structure elementwise. As I argued above, I think for |
It's a bad idea to have behaviour change depending on the type, it will just lead to hard to debug bugs. Perhaps anything that's defined in an abstract algebra sense ( |
Indeed, that would be a good check for consistency: |
This business of interpreting of matrices of matrices as representing block matrices in some vague, unspecified way is pretty questionable, imo. If we're going to do it, I think that we at least deserve a description of how it's supposed to work. Julia is, after all, not some type-impoverished language that can't do this in a better way with actual types. |
The existence of BlockArrays.jl doesn't change the fact that Julia arrays can have array elements and we need to consider what is the right behavior for such arrays in our algorithms. Treating elements as scalars is not a neutral position. The issues associated with arrays of arrays is something we gradually have understood and we will need to continue to discuss it. It isn't helpful to try to keep the status quo and point to external packages when the problem is completely within the scope of |
There's a pretty alpha, soon-to-be registered BlockDiagonal.jl package (Obviously, as @andreasnoack says, this doesn't solve any problems in the scope of |
All I've asked for (repeatedly) is a clarification of what the block array model even is. Have yet to get it. |
I would say any sensible model would at the very least have the property that operations on matrix-representations of the imaginary numbers behave the same way as imaginary numbers, or throw errors. Matrix multiplication satisfies this property: julia> i = [0 1; -1 0];
julia> A = reshape([I+2i,I-i,2I-3i,3I+4i], 2,2)
2×2 Array{Array{Int64,2},2}:
[1 2; -2 1] [2 -3; 3 2]
[1 -1; 1 1] [3 4; -4 3]
julia> B = [1+2im 2-3im; 1-im 3+4im]
2×2 Array{Complex{Int64},2}:
1+2im 2-3im
1-1im 3+4im
julia> A*[I+i,2I-i]
2-element Array{Array{Int64,2},1}:
[0 -5; 5 0]
[12 5; -5 12]
julia> B*[1+im,2-im]
2-element Array{Complex{Int64},1}:
0 - 5im
12 + 5im
julia> A'
2×2 Adjoint{Adjoint{Int64,Array{Int64,2}},Array{Array{Int64,2},2}}:
[1 -2; 2 1] [1 1; -1 1]
[2 3; -3 2] [3 -4; 4 3]
julia> B'
2×2 Adjoint{Complex{Int64},Array{Complex{Int64},2}}:
1-2im 1+1im
2+3im 3-4im
julia> transpose(A)
2×2 Transpose{Transpose{Int64,Array{Int64,2}},Array{Array{Int64,2},2}}:
[1 -2; 2 1] [1 1; -1 1]
[2 3; -3 2] [3 -4; 4 3]
julia> transpose(B)
2×2 Transpose{Complex{Int64},Array{Complex{Int64},2}}:
1+2im 1-1im
2-3im 3+4im The current behaviour of Based on this model, it makes sense that |
Currently, block diagonal matrices don't correctly support
istril
oristriu
These can be solved by adding
etc.
Once this is fixed, what should the intended behavior of
tril(D, k)
,triu(D, k)
,diag(D, k)
, etc. be?tril(D, k)
can just recursively check the blocks but should we makediag(D, k)
actually return the k-th super diagonal of the 'full' matrix?I realize this is quite low on the priority list, but it seems like block diagonal matrices were hastily added and a lot of support is missing.
The text was updated successfully, but these errors were encountered: