mirror of
https://github.com/Relintai/pandemonium_engine_easy_charts.git
synced 2024-12-23 13:57:01 +01:00
add matrix methods
This commit is contained in:
parent
59a98fc8d8
commit
006fa4de7f
@ -16,6 +16,10 @@ func update_row(row : Array, index : int) -> void:
|
||||
assert(rows() > index, "the row size must match matrix row size")
|
||||
values[index] = row
|
||||
|
||||
func remove_row(index: int) -> void:
|
||||
assert(rows() > index, "the row size must match matrix row size")
|
||||
values.remove(index)
|
||||
|
||||
func insert_column(column : Array, index : int = values[0].size()) -> void:
|
||||
if columns() != 0:
|
||||
assert(column.size() == rows(), "the column size must match matrix column size")
|
||||
@ -27,6 +31,11 @@ func update_column(column : Array, index : int) -> void:
|
||||
for row_idx in column.size():
|
||||
values[row_idx][index] = column[row_idx]
|
||||
|
||||
func remove_column(index: int) -> void:
|
||||
assert(columns() > index, "the column index must be at least equals to the rows count")
|
||||
for row in get_rows():
|
||||
row.remove(index)
|
||||
|
||||
func resize(rows: int, columns: int) -> void:
|
||||
for row in range(rows):
|
||||
var row_column: Array = []
|
||||
@ -45,6 +54,12 @@ func rows() -> int:
|
||||
func columns() -> int:
|
||||
return values[0].size() if rows() != 0 else 0
|
||||
|
||||
func value(row: int, column: int) -> float:
|
||||
return values[row][column]
|
||||
|
||||
func set_value(value: float, row: int, column: int) -> void:
|
||||
values[row][column] = value
|
||||
|
||||
func get_column(column : int) -> Array:
|
||||
assert(column < columns(), "index of the column requested (%s) exceedes matrix columns (%s)"%[column, columns()])
|
||||
var column_array : Array = []
|
||||
@ -67,9 +82,64 @@ func get_rows(from : int = 0, to : int = rows()-1) -> Array:
|
||||
return values.slice(from, to)
|
||||
# return MatrixGenerator.from_array(values)
|
||||
|
||||
func empty() -> bool:
|
||||
func is_empty() -> bool:
|
||||
return rows() == 0 and columns() == 0
|
||||
|
||||
|
||||
func is_square() -> bool:
|
||||
return columns() == rows()
|
||||
|
||||
|
||||
func is_diagonal() -> bool:
|
||||
if not is_square():
|
||||
return false
|
||||
|
||||
for i in rows():
|
||||
for j in columns():
|
||||
if i != j and values[i][j] != 0:
|
||||
return false
|
||||
|
||||
return true
|
||||
|
||||
|
||||
func is_upper_triangular() -> bool:
|
||||
if not is_square():
|
||||
return false
|
||||
|
||||
for i in rows():
|
||||
for j in columns():
|
||||
if i > j and values[i][j] != 0:
|
||||
return false
|
||||
|
||||
return true
|
||||
|
||||
|
||||
func is_lower_triangular() -> bool:
|
||||
if not is_square():
|
||||
return false
|
||||
|
||||
for i in rows():
|
||||
for j in columns():
|
||||
if i < j and values[i][j] != 0:
|
||||
return false
|
||||
|
||||
return true
|
||||
|
||||
|
||||
func is_triangular() -> bool:
|
||||
return is_upper_triangular() or is_lower_triangular()
|
||||
|
||||
|
||||
func is_identity() -> bool:
|
||||
if not is_diagonal():
|
||||
return false
|
||||
|
||||
for i in rows():
|
||||
if values[i][i] != 1:
|
||||
return false
|
||||
|
||||
return true
|
||||
|
||||
func _to_string() -> String:
|
||||
var last_string_len : int
|
||||
for row in values:
|
||||
@ -83,6 +153,11 @@ func _to_string() -> String:
|
||||
string+="\n"
|
||||
return string
|
||||
|
||||
# ----
|
||||
func set(position: String, value) -> void:
|
||||
var t_pos: Array = position.split(",")
|
||||
values[t_pos[0]][t_pos[1]] = value
|
||||
|
||||
# --------------
|
||||
func _get(_property : String):
|
||||
# ":" --> Columns
|
||||
|
@ -2,6 +2,15 @@ tool
|
||||
extends Reference
|
||||
class_name MatrixGenerator
|
||||
|
||||
static func zeros(rows: int, columns: int) -> Matrix:
|
||||
var zeros: Array = []
|
||||
var t_rows: Array = []
|
||||
t_rows.resize(columns)
|
||||
t_rows.fill(0.0)
|
||||
for row in rows:
|
||||
zeros.append(t_rows.duplicate())
|
||||
return Matrix.new(zeros)
|
||||
|
||||
# Generates a Matrix with random values between [from; to] with a given @size (rows, columns)
|
||||
static func random_float_range(from : float, to : float, size : Vector2, _seed : int = 1234) -> Matrix:
|
||||
seed(_seed)
|
||||
@ -33,6 +42,55 @@ static func sub_matrix(_matrix : Matrix, from : PoolIntArray, to : PoolIntArray)
|
||||
static func duplicate(_matrix : Matrix) -> Matrix:
|
||||
return Matrix.new(_matrix.to_array().duplicate())
|
||||
|
||||
# Calculate the determinant of a matrix
|
||||
static func determinant(matrix: Matrix) -> float:
|
||||
assert(matrix.is_square(), "Expected square matrix")
|
||||
|
||||
var determinant: float = 0.0
|
||||
|
||||
if matrix.rows() == 2 :
|
||||
determinant = (matrix.value(0, 0) * matrix.value(1, 1)) - (matrix.value(0, 1) * matrix.value(1, 0))
|
||||
elif matrix.is_diagonal() or matrix.is_triangular() :
|
||||
for i in matrix.rows():
|
||||
determinant *= matrix.value(i, i)
|
||||
elif matrix.is_identity() :
|
||||
determinant = 1.0
|
||||
else:
|
||||
# Laplace expansion
|
||||
var multiplier: float = -1.0
|
||||
var submatrix: Matrix = sub_matrix(matrix, [1, 0], [matrix.rows(), matrix.columns()])
|
||||
for j in matrix.columns() :
|
||||
var cofactor: Matrix = copy(submatrix)
|
||||
cofactor.remove_column(j)
|
||||
multiplier *= -1.0
|
||||
determinant += multiplier * matrix.value(0, j) * determinant(cofactor)
|
||||
|
||||
return determinant
|
||||
|
||||
|
||||
# Calculate the inverse of a Matrix
|
||||
static func inverse(matrix: Matrix) -> Matrix:
|
||||
var inverse: Matrix
|
||||
|
||||
# Minors and Cofactors
|
||||
var minors_cofactors: Matrix = zeros(matrix.rows(), matrix.columns())
|
||||
var multiplier: float = -1.0
|
||||
|
||||
for i in minors_cofactors.rows():
|
||||
for j in minors_cofactors.columns():
|
||||
var t_minor: Matrix = copy(matrix)
|
||||
t_minor.remove_row(i)
|
||||
t_minor.remove_column(j)
|
||||
multiplier *= -1.0
|
||||
minors_cofactors.set_value(multiplier * determinant(t_minor), i, j)
|
||||
|
||||
var transpose: Matrix = transpose(minors_cofactors)
|
||||
var determinant: float = determinant(matrix)
|
||||
|
||||
inverse = multiply_float(transpose, 1 / determinant)
|
||||
|
||||
return inverse
|
||||
|
||||
# Transpose a given Matrix
|
||||
static func transpose(_matrix : Matrix) -> Matrix:
|
||||
var array : Array = []
|
||||
@ -93,6 +151,10 @@ static func multiply_float(_matrix1 : Matrix, _float : float) -> Matrix:
|
||||
array[x][y]*=_float
|
||||
return Matrix.new(array)
|
||||
|
||||
|
||||
static func copy(matrix: Matrix) -> Matrix:
|
||||
return Matrix.new(matrix.values.duplicate(true))
|
||||
|
||||
# ------------------------------------------------------------
|
||||
static func get_letter_index(index : int) -> String:
|
||||
return "A B C D E F G H I J K L M N O P Q R S T U V W X Y Z".split(" ")[index]
|
||||
|
Loading…
Reference in New Issue
Block a user