diff options
author | marcandre <marcandre@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2011-06-29 01:11:19 +0000 |
---|---|---|
committer | marcandre <marcandre@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2011-06-29 01:11:19 +0000 |
commit | de97e946f04dd0374d6f2580c97591bc1fdc1f3f (patch) | |
tree | 21a6ddc936d458f3357a42dff9a1ca2072e65c02 /lib/matrix.rb | |
parent | 22ffae4009c90eabf5a4e1f73caeaf3256f4e16c (diff) |
* lib/matrix.rb: Add Matrix#diagonal?, hermitian?, normal?, orthogonal?
permutation?, symmetric?, {lower|upper}triangular?, unitary?, zero?
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@32279 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
Diffstat (limited to 'lib/matrix.rb')
-rw-r--r-- | lib/matrix.rb | 138 |
1 files changed, 138 insertions, 0 deletions
diff --git a/lib/matrix.rb b/lib/matrix.rb index 7978bb9de3..02c157801d 100644 --- a/lib/matrix.rb +++ b/lib/matrix.rb @@ -60,11 +60,21 @@ end # * <tt> #minor(*param) </tt> # # Properties of a matrix: +# * <tt> #diagonal? </tt> # * <tt> #empty? </tt> +# * <tt> #hermitian? </tt> +# * <tt> #lower_triangular? </tt> +# * <tt> #normal? </tt> +# * <tt> #orthogonal? </tt> +# * <tt> #permutation? </tt> # * <tt> #real? </tt> # * <tt> #regular? </tt> # * <tt> #singular? </tt> # * <tt> #square? </tt> +# * <tt> #symmetric? </tt> +# * <tt> #unitary? </tt> +# * <tt> #upper_triangular? </tt> +# * <tt> #zero? </tt> # # Matrix arithmetic: # * <tt> *(m) </tt> @@ -572,6 +582,15 @@ class Matrix #++ # + # Returns +true+ is this is a diagonal matrix. + # Raises an error if matrix is not square. + # + def diagonal? + Matrix.Raise ErrDimensionMismatch unless square? + each(:off_diagonal).all?(&:zero?) + end + + # # Returns +true+ if this is an empty matrix, i.e. if the number of rows # or the number of columns is 0. # @@ -580,6 +599,82 @@ class Matrix end # + # Returns +true+ is this is an hermitian matrix. + # Raises an error if matrix is not square. + # + def hermitian? + Matrix.Raise ErrDimensionMismatch unless square? + each_with_index(:strict_upper).all? do |e, row, col| + e == rows[col][row].conj + end + end + + # + # Returns +true+ is this is a lower triangular matrix. + # + def lower_triangular? + each(:strict_upper).all?(&:zero?) + end + + # + # Returns +true+ is this is a normal matrix. + # Raises an error if matrix is not square. + # + def normal? + Matrix.Raise ErrDimensionMismatch unless square? + rows.each_with_index do |row_i, i| + rows.each_with_index do |row_j, j| + s = 0 + rows.each_with_index do |row_k, k| + s += row_i[k] * row_j[k].conj - row_k[i].conj * row_k[j] + end + return false unless s == 0 + end + end + true + end + + # + # Returns +true+ is this is an orthogonal matrix + # Raises an error if matrix is not square. + # + def orthogonal? + Matrix.Raise ErrDimensionMismatch unless square? + rows.each_with_index do |row, i| + column_size.times do |j| + s = 0 + row_size.times do |k| + s += row[k] * rows[k][j] + end + return false unless s == (i == j ? 1 : 0) + end + end + true + end + + # + # Returns +true+ is this is a permutation matrix + # Raises an error if matrix is not square. + # + def permutation? + Matrix.Raise ErrDimensionMismatch unless square? + cols = Array.new(column_size) + rows.each_with_index do |row, i| + found = false + row.each_with_index do |e, j| + if e == 1 + return false if found || cols[j] + found = cols[j] = true + elsif e != 0 + return false + end + end + return false unless found + end + true + end + + # # Returns +true+ if all entries of the matrix are real. # def real? @@ -607,6 +702,49 @@ class Matrix column_size == row_size end + # + # Returns +true+ is this is a symmetric matrix. + # Raises an error if matrix is not square. + # + def symmetric? + Matrix.Raise ErrDimensionMismatch unless square? + each_with_index(:strict_upper).all? do |e, row, col| + e == rows[col][row] + end + end + + # + # Returns +true+ is this is a unitary matrix + # Raises an error if matrix is not square. + # + def unitary? + Matrix.Raise ErrDimensionMismatch unless square? + rows.each_with_index do |row, i| + column_size.times do |j| + s = 0 + row_size.times do |k| + s += row[k].conj * rows[k][j] + end + return false unless s == (i == j ? 1 : 0) + end + end + true + end + + # + # Returns +true+ is this is an upper triangular matrix. + # + def upper_triangular? + each(:strict_lower).all?(&:zero?) + end + + # + # Returns +true+ is this is a matrix with only zero elements + # + def zero? + all?(&:zero?) + end + #-- # OBJECT METHODS -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- #++ |