MathGroup Archive 2010

[Date Index] [Thread Index] [Author Index]

Search the Archive

Re: It would be nice to have DiagonalMatrix accept a matrix as building

  • To: mathgroup at smc.vnet.net
  • Subject: [mg113512] Re: It would be nice to have DiagonalMatrix accept a matrix as building
  • From: Zach Bjornson <bjornson at stanford.edu>
  • Date: Sun, 31 Oct 2010 05:22:01 -0500 (EST)
  • References: <iajcai$p6j$1@smc.vnet.net>

(this is probably better submitted to Wolfram as a feature request, 
they're very responsive)

You can use Band to avoid looping constructs:

DiagonalM[block_, nBlocks_] :=
  Normal@
   SparseArray[Band[{1, 1}] -> ConstantArray[block, {nBlocks}]]

I thought there was a still shorter version, but can't recall it...

Best,
Zach

On 10/31/2010 2:19 AM, Nasser M. Abbasi wrote:
> Sometime there is a need to make a matrix with repeating subblocks on
> the diagonal.  For example, one might want to create matrix A, with
> matrix B on its diagonal, repeated n times.
>
> DiagonalMatrix only accepts vector (list), not matrix (list of lists),
> as its argument.
>
> So, one has the option to use DiagonalMatrix, repeatedly, using
> different offsets at a time, and manually layout the diagonal. Or use
> SparseArray since SparseArray accepts a matrix as the band, but also
> make a loop to add the block at different locations on the diagonal.
>
> The SparseArray method is little less work, but I think a nice solution
> would be to have the ability to specify the block, and how many time it
> needs to be repeated on the diagonal. That other 'system' has this
> command to do that.
>
> This is how I now create a diagonalMatrix with matrices at its diagonal.
> Maybe an expert here knows of a short way or trick to use.
>
> In this example, I wanted to make matrix 'a' with the submatrix
>
>               {{1,2}{3,4}}
>
> on its diagonal, and wanted this repeated 6 times. So, I made a large
> cup of coffee, sat down and wrote this
>
> ----------------------------
> block={{1,2},{3,4}};
> sizeOfBlock=Length[block];
> nBlocks=6;
> a=Table[0,{i,sizeOfBlock*nBlocks},{j,sizeOfBlock*nBlocks}];
> Do[
> a=a+Normal@SparseArray[Band[{i*sizeOfBlock+1,i*sizeOfBlock+1}]->block,nBlocks*sizeOfBlock],
> {i,0,nBlocks-1}
> ];
> --------------------------
>
> {{1,2,0,0,0,0,0,0,0,0,0,0},{3,4,0,0,0,0,0,0,0,0,0,0},
> {0,0,1,2,0,0,0,0,0,0,0,0},{0,0,3,4,0,0,0,0,0,0,0,0},
> {0,0,0,0,1,2,0,0,0,0,0,0},{0,0,0,0,3,4,0,0,0,0,0,0},
> {0,0,0,0,0,0,1,2,0,0,0,0},{0,0,0,0,0,0,3,4,0,0,0,0},
> {0,0,0,0,0,0,0,0,1,2,0,0},{0,0,0,0,0,0,0,0,3,4,0,0},
> {0,0,0,0,0,0,0,0,0,0,1,2},{0,0,0,0,0,0,0,0,0,0,3,4}}
>
> So, it works.
>
> But if what I had imagined existed, I should have been able to do
>
> DiagonalMatrix[block,0,6]
>
> Again, the above command would only work if 'block' was a 1-D list, not
> a 2-D list (ie. a matrix).
>
> of course, I can make a function and hide the code I wrote inside this
> function, and it would just look the same as the call that I wanted.
>
> All what I am saying is that Mathematica should support this feature as
> part of DiagonalMatrix as it is very common thing.
>
> thanks
> --Nasser


  • Prev by Date: Re: How does Plot* functions know about range?
  • Next by Date: Re: Assertions in Mathematica?
  • Previous by thread: It would be nice to have DiagonalMatrix accept a matrix as building