from Triangular and diagonal indexing by Bruno Luong
A collection of functions to index diagonal and triangular parts of the matrix

EliminationM(n, varargin)
function M = EliminationM(n, varargin)
% function M = EliminationM(n)
% M = EliminationM(n, 'lo') % (default) OR
% M = EliminationM(n, 'up') % Matrix to extract upper part
% M = EliminationM(..., k) % 
% Return elimination matrix order n
%
% Input k is optional shifting. For k=0, extract from the main
% diagonal. For k>0 -> above the diagonal, k<0 -> below the diagonal
%
% Ouput are sparse
%
% EliminationM(size(A),'lo')*A(:) == A(itril(size(A))) % <- all true
% EliminationM(size(A),'up')*A(:) == A(itriu(size(A))) % <- all true
%
% Author: Bruno Luong <brunoluong@yahoo.com>
% Date: 21/March/2009
%
% Ref : Magnus, Jan R.; Neudecker, Heinz (1980), "The elimination matrix:
% some lemmas and applications", Society for Industrial and Applied Mathematics.
% Journal on Algebraic and Discrete Methods 1 (4): 422449,  
% doi:10.1137/0601049, ISSN 0196-5212.

option = 'lo';  % lower by default
k = 0; % Main diagonal by default

% Parse optional inputs
% We allow only two options {'lo', 'up'} and k
for narg=1:length(varargin)
    if ischar(varargin{narg}) % {'lo', 'up'}
        option = varargin{narg};
    elseif isnumeric(varargin{narg}) % k
        k = varargin{narg};
    end
end

if isscalar(n)
    n = [n n];
end

switch lower(option(1))
    case 'l' % u, lo, LO, LOWER ...
        I = itril(n,k);
    case 'u' % u, up, UP, UPPER ...
        I = itriu(n,k);
    otherwise
        error('option must be ''lo'' or ''up''');       
end

% Result
M = sparse((1:length(I)).', I, 1, length(I), prod(n));

end

Contact us at files@mathworks.com