June 2018 Update

This commit is contained in:
Ingy döt Net 2018-06-22 20:57:24 +00:00
parent ba8067c3b7
commit 22f33d4004
5278 changed files with 84726 additions and 14379 deletions

View file

@ -1,4 +1,7 @@
{{omit from|GUISS}}
;Task:
Show how to compute the '''reduced row echelon form'''
(a.k.a. '''row canonical form''') of a matrix.
@ -37,10 +40,15 @@ Built-in functions or this pseudocode (from Wikipedia) may be used:
'''end function'''
For testing purposes, the RREF of this matrix:
<pre>1 2 -1 -4
2 3 -1 -11
-2 0 -3 22</pre>
<pre>
1 2 -1 -4
2 3 -1 -11
-2 0 -3 22
</pre>
is:
<pre>1 0 0 -8
0 1 0 1
0 0 1 -2</pre>
<pre>
1 0 0 -8
0 1 0 1
0 0 1 -2
</pre>
<br><br>

View file

@ -28,7 +28,7 @@ rref(list l, integer rows, integer columns)
u = l[i];
l_spin(l, i, r);
l.spin(i, r);
e = u[lead];
if (e) {
for (j, f in u) {
@ -40,7 +40,7 @@ rref(list l, integer rows, integer columns)
if (i != r) {
e = v[lead];
for (j, f in v) {
v[j] = f - l_q_integer(u, j) * e;
v[j] = f - u[j] * e;
}
}
}
@ -52,14 +52,12 @@ rref(list l, integer rows, integer columns)
}
void
display_2(list l, integer rows, integer columns)
display_2(list l)
{
integer i;
list u;
i = 0;
for (i, u in l) {
l_ucall(u, o_winteger, -1, 4);
for (, u in l) {
u.ucall(o_winteger, -1, 4);
o_byte('\n');
}
}
@ -69,11 +67,11 @@ main(void)
{
list l;
l = l_effect(l_effect(1, 2, -1, -4),
l_effect(2, 3, -1, -11),
l_effect(-2, 0, -3, 22));
l = list(list(1, 2, -1, -4),
list(2, 3, -1, -11),
list(-2, 0, -3, 22));
rref(l, 3, 4);
display_2(l, 3, 4);
display_2(l);
return 0;
}

View file

@ -1,10 +1,36 @@
]mymatrix=: _4]\ 1 2 _1 _4 2 3 _1 _11 _2 0 _3 22
1 2 _1 _4
2 3 _1 _11
_2 0 _3 22
NB.*pivot v Pivot at row, column
NB. form: (row,col) pivot M
pivot=: dyad define
'r c'=. x
col=. c{"1 y
y - (col - r = i.#y) */ (r{y) % r{col
)
require 'math/misc/linear'
gauss_jordan mymatrix
1 0 0 _8
0 1 0 1
0 0 1 _2
NB.*gauss_jordan v Gauss-Jordan elimination (full pivoting)
NB. y is: matrix
NB. x is: optional minimum tolerance, default 1e_15.
NB. If a column below the current pivot has numbers of magnitude all
NB. less then x, it is treated as all zeros.
gauss_jordan=: verb define
1e_15 gauss_jordan y
:
mtx=. y
'r c'=. $mtx
rows=. i.r
i=. j=. 0
max=. i.>./
while. (i<r) *. j<c do.
k=. max col=. | i}. j{"1 mtx
if. 0 < x-k{col do. NB. if all col < tol, set to 0:
mtx=. 0 (<(i}.rows);j) } mtx
else. NB. otherwise sort and pivot:
if. k do.
mtx=. (<i,i+k) C. mtx
end.
mtx=. (i,j) pivot mtx
i=. >:i
end.
j=. >:j
end.
mtx
)

View file

@ -1,16 +1,10 @@
gauss_jordan 2 0 _1 0 0,1 0 0 _1 0,3 0 0 _2 _1,0 1 0 0 _2,:0 1 _1 0 0
1 0 0 0 _1
0 1 0 0 _2
0 0 1 0 _2
0 0 0 1 _1
0 0 0 0 0
gauss_jordan 1 2 3 4 3 1,2 4 6 2 6 2,3 6 18 9 9 _6,4 8 12 10 12 4,:5 10 24 11 15 _4
1 2 0 0 3 0
0 0 1 0 0 0
0 0 0 1 0 0
0 0 0 0 0 1
0 0 0 0 0 0
gauss_jordan 0 1,1 2,:0 5
1 0
0 1
0 0
require 'math/misc/linear'
]A=: 1 2 _1 _4 , 2 3 _1 _11 ,: _2 0 _3 22
1 2 _1 _4
2 3 _1 _11
_2 0 _3 22
gauss_jordan A
1 0 0 _8
0 1 0 1
0 0 1 _2

View file

@ -1,37 +1,16 @@
mat=:".;._2]0 :0
1 0 0 0 0 0 1 0 0 0 0 _1 0 0 0 0 0 0
1 0 0 0 0 0 0 1 0 0 0 0 _1 0 0 0 0 0
1 0 0 0 0 0 0 0 1 0 0 0 0 _1 0 0 0 0
0 1 0 0 0 0 1 0 0 0 0 0 0 0 _1 0 0 0
0 1 0 0 0 0 0 0 1 0 0 _1 0 0 0 0 0 0
0 1 0 0 0 0 0 0 0 0 1 0 0 0 0 0 _1 0
0 0 1 0 0 0 1 0 0 0 0 0 _1 0 0 0 0 0
0 0 1 0 0 0 0 0 0 1 0 0 0 0 _1 0 0 0
0 0 0 1 0 0 0 1 0 0 0 0 0 0 0 _1 0 0
0 0 0 1 0 0 0 0 0 1 0 0 _1 0 0 0 0 0
0 0 0 0 1 0 0 1 0 0 0 0 0 _1 0 0 0 0
0 0 0 0 1 0 0 0 1 0 0 0 0 0 0 0 _1 0
0 0 0 0 1 0 0 0 0 0 1 0 0 0 0 _1 0 0
0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 1
0 0 0 0 0 1 0 0 0 0 1 0 0 0 _1 0 0 0
)
gauss_jordan mat
1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0.435897
0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0.307692
0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0.512821
0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0.717949
0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0.487179
0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0.205128
0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0.282051
0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0.333333
0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0.512821
0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0.641026
0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0.717949
0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 0.769231
0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0.512821
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 1
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0.820513
gauss_jordan 2 0 _1 0 0,1 0 0 _1 0,3 0 0 _2 _1,0 1 0 0 _2,:0 1 _1 0 0
1 0 0 0 _1
0 1 0 0 _2
0 0 1 0 _2
0 0 0 1 _1
0 0 0 0 0
gauss_jordan 1 2 3 4 3 1,2 4 6 2 6 2,3 6 18 9 9 _6,4 8 12 10 12 4,:5 10 24 11 15 _4
1 2 0 0 3 0
0 0 1 0 0 0
0 0 0 1 0 0
0 0 0 0 0 1
0 0 0 0 0 0
gauss_jordan 0 1,1 2,:0 5
1 0
0 1
0 0

View file

@ -0,0 +1,37 @@
mat=: 0 ". ];._2 noun define
1 0 0 0 0 0 1 0 0 0 0 _1 0 0 0 0 0 0
1 0 0 0 0 0 0 1 0 0 0 0 _1 0 0 0 0 0
1 0 0 0 0 0 0 0 1 0 0 0 0 _1 0 0 0 0
0 1 0 0 0 0 1 0 0 0 0 0 0 0 _1 0 0 0
0 1 0 0 0 0 0 0 1 0 0 _1 0 0 0 0 0 0
0 1 0 0 0 0 0 0 0 0 1 0 0 0 0 0 _1 0
0 0 1 0 0 0 1 0 0 0 0 0 _1 0 0 0 0 0
0 0 1 0 0 0 0 0 0 1 0 0 0 0 _1 0 0 0
0 0 0 1 0 0 0 1 0 0 0 0 0 0 0 _1 0 0
0 0 0 1 0 0 0 0 0 1 0 0 _1 0 0 0 0 0
0 0 0 0 1 0 0 1 0 0 0 0 0 _1 0 0 0 0
0 0 0 0 1 0 0 0 1 0 0 0 0 0 0 0 _1 0
0 0 0 0 1 0 0 0 0 0 1 0 0 0 0 _1 0 0
0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 1
0 0 0 0 0 1 0 0 0 0 1 0 0 0 _1 0 0 0
)
gauss_jordan mat
1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0.435897
0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0.307692
0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0.512821
0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0.717949
0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0.487179
0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0.205128
0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0.282051
0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0.333333
0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0.512821
0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0.641026
0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0.717949
0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 0.769231
0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0.512821
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 1
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0.820513

View file

@ -0,0 +1,80 @@
// version 1.1.51
typealias Matrix = Array<DoubleArray>
/* changes the matrix to RREF 'in place' */
fun Matrix.toReducedRowEchelonForm() {
var lead = 0
val rowCount = this.size
val colCount = this[0].size
for (r in 0 until rowCount) {
if (colCount <= lead) return
var i = r
while (this[i][lead] == 0.0) {
i++
if (rowCount == i) {
i = r
lead++
if (colCount == lead) return
}
}
val temp = this[i]
this[i] = this[r]
this[r] = temp
if (this[r][lead] != 0.0) {
val div = this[r][lead]
for (j in 0 until colCount) this[r][j] /= div
}
for (k in 0 until rowCount) {
if (k != r) {
val mult = this[k][lead]
for (j in 0 until colCount) this[k][j] -= this[r][j] * mult
}
}
lead++
}
}
fun Matrix.printf(title: String) {
println(title)
val rowCount = this.size
val colCount = this[0].size
for (r in 0 until rowCount) {
for (c in 0 until colCount) {
if (this[r][c] == -0.0) this[r][c] = 0.0 // get rid of negative zeros
print("${"% 6.2f".format(this[r][c])} ")
}
println()
}
println()
}
fun main(args: Array<String>) {
val matrices = listOf(
arrayOf(
doubleArrayOf( 1.0, 2.0, -1.0, -4.0),
doubleArrayOf( 2.0, 3.0, -1.0, -11.0),
doubleArrayOf(-2.0, 0.0, -3.0, 22.0)
),
arrayOf(
doubleArrayOf(1.0, 2.0, 3.0, 4.0, 3.0, 1.0),
doubleArrayOf(2.0, 4.0, 6.0, 2.0, 6.0, 2.0),
doubleArrayOf(3.0, 6.0, 18.0, 9.0, 9.0, -6.0),
doubleArrayOf(4.0, 8.0, 12.0, 10.0, 12.0, 4.0),
doubleArrayOf(5.0, 10.0, 24.0, 11.0, 15.0, -4.0)
)
)
for (m in matrices) {
m.printf("Original matrix:")
m.toReducedRowEchelonForm()
m.printf("Reduced row echelon form:")
}
}

View file

@ -1,25 +1,21 @@
sub rref (@m) {
@m or return;
return unless @m;
my ($lead, $rows, $cols) = 0, +@m, +@m[0];
for ^$rows -> $r {
return @m if $lead >= $cols;
$lead < $cols or return @m;
my $i = $r;
until @m[$i][$lead] {
until @m[$i;$lead] {
++$i == $rows or next;
$i = $r;
++$lead == $cols and return @m;
}
@m[$i, $r] = @m[$r, $i];
my $lv = @m[$r][$lead];
@m[$i, $r] = @m[$r, $i] if $r != $i;
my $lv = @m[$r;$lead];
@m[$r] »/=» $lv;
for ^$rows -> $n {
next if $n == $r;
@m[$n] »-=» @m[$r] »*» @m[$n][$lead];
@m[$n] »-=» @m[$r] »*» (@m[$n;$lead] // 0);
}
++$lead;
}

View file

@ -3,44 +3,45 @@ cols=0; w=0; @.=0 /*max cols in a row; max width;
mat.=; mat.1= ' 1 2 -1 -4 '
mat.2= ' 2 3 -1 -11 '
mat.3= ' -2 0 -3 22 '
do r=1 until mat.r==''; _=mat.r /*build @.row.col from (matrix) mat.X*/
do c=1 until _=''; parse var _ @.r.c _
w=max(w, length(@.r.c) +1) /*find the maximum width of an element.*/
end /*c*/
cols=max(cols,c) /*remember max number of cols.*/
do r=1 until mat.r==''; _=mat.r /*build @.row.col from (matrix) mat.X*/
do c=1 until _=''; parse var _ @.r.c _
w=max(w, length(@.r.c) + 1) /*find the maximum width of an element.*/
end /*c*/
cols=max(cols, c) /*save the maximum number of columns. */
end /*r*/
rows=r-1 /*adjust the row count (from DO loop).*/
rows=r - 1 /*adjust the row count (from DO loop).*/
call showMat 'original matrix' /*display the original matrix to screen*/
!=1 /*set the working column pointer to 1.*/
/* ┌─────────────────────────────────────────◄── Reduced Row Echelon Form on matrix.*/
/* ┌──────────────────────────────────────◄──── Reduced Row Echelon Form on matrix.*/
do r=1 for rows while cols>! /*begin to perform the heavy lifting. */
j=r
do while @.j.!==0; j=j+1
if j==rows then do; j=r; !=!+1; if cols==! then leave r; end
j=r /*use a subsitute index for the DO loop*/
do while @.j.!==0; j=j + 1
if j==rows then do; j=r; !=! + 1; if cols==! then leave r; end
end /*while*/
/* [↓] swap rows J,R (but not if same)*/
do _=1 for cols while j\==r; parse value @.r._ @.j._ with @.j._ @._._; end /*_*/
do _=1 for cols while j\==r; parse value @.r._ @.j._ with @.j._ @._._
end /*_*/
?=@.r.!
do d=1 for cols while ?\=1; @.r.d=@.r.d/?; end /*d*/
/* [↑] divide row J by @.r.p ──unless≡1*/
do k=1 for rows; ?=@.k.! /*subtract (row K) @.r.s from row K.*/
if k==r | ?=0 then iterate /*skip if row K is the same as row R.*/
do s=1 for cols; @.k.s=@.k.s - ?*@.r.s; end /*s*/
end /*k*/ /* [↑] for the rest of numbers in row.*/
!=!+1 /*bump the column pointer. */
do d=1 for cols while ?\=1; @.r.d= @.r.d / ?
end /*d*/ /* [↑] divide row J by @.r.p ──unless≡1*/
do k=1 for rows; ?= @.k.! /*subtract (row K) @.r.s from row K.*/
if k==r | ?=0 then iterate /*skip if row K is the same as row R.*/
do s=1 for cols; @.k.s= @.k.s - ? * @.r.s
end /*s*/
end /*k*/ /* [↑] for the rest of numbers in row.*/
!=! + 1 /*bump the column pointer. */
end /*r*/
call showMat 'matrix RREF' /*display the reduced row echelon form.*/
exit /*stick a fork in it, we're all done. */
/*──────────────────────────────────────────────────────────────────────────────────────*/
showMat: parse arg title; say; say center(title, 3+(cols+1)*w, ''); say
showMat: parse arg title; say; say center(title, 3 + (cols+1) * w, ''); say
do r=1 for rows; _=
do c=1 for cols
if @.r.c=='' then do; say "***error*** matrix element isn't defined:"
say 'row' row", column" c'.'; exit 13
say 'row' r", column" c'.'; exit 13
end
_=_ right(@.r.c,w)
_=_ right(@.r.c, w)
end /*c*/
say _ /*display a row of the matrix to screen*/
end /*r*/
return
say _ /*display a matrix row to the terminal.*/
end /*r*/; return

View file

@ -0,0 +1,60 @@
# Project : Reduced row echelon form
# Date : 2017/12/27
# Author : Gal Zsolt (~ CalmoSoft ~)
# Email : <calmosoft@gmail.com>
matrix = [[1, 2, -1, -4],
[2, 3, -1, -11],
[ -2, 0, -3, 22]]
ref(matrix)
for row = 1 to 3
for col = 1 to 4
if matrix[row][col] = -0
see "0 "
else
see "" + matrix[row][col] + " "
ok
next
see nl
next
func ref(m)
nrows = 3
ncols = 4
lead = 1
for r = 1 to nrows
if lead >= ncols
exit
ok
i = r
while m[i][lead] = 0
i = i + 1
if i = nrows
i = r
lead = lead + 1
if lead = ncols
exit 2
ok
ok
end
for j = 1 to ncols
temp = m[i][j]
m[i][j] = m[r][j]
m[r][j] = temp
next
n = m[r][lead]
if n != 0
for j = 1 to ncols
m[r][j] = m[r][j] / n
next
ok
for i = 1 to nrows
if i != r
n = m[i][lead]
for j = 1 to ncols
m[i][j] = m[i][j] - m[r][j] * n
next
ok
next
lead = lead + 1
next

View file

@ -1,28 +1,27 @@
func rref (Array m) {
m.is_empty && return;
var (lead, rows, cols) = (0, m.len, m[0].len);
func rref (M) {
var (j, rows, cols) = (0, M.len, M[0].len)
rows.range.each { |r|
lead >= cols && return m;
var i = r;
for r in (^rows) {
j < cols || return M
while (!m[i][lead]) {
++i == rows || next;
i = r;
++lead == cols && return m;
var i = r
while (!M[i][j]) {
++i == rows || next
i = r
++j == cols && return M
}
m[i, r] = m[r, i];
var lv = m[r][lead];
m[r] = (m[r] »/» lv);
M[i, r] = M[r, i] if (r != i)
M[r] = (M[r] »/» M[r][j])
rows.range.each { |n|
n == r && next;
m[n] = (m[n] »-« (m[r] «*« m[n][lead]))
for n in (^rows) {
next if (n == r)
M[n] = (M[n] »-« (M[r] »*» M[n][j]))
}
++lead;
++j
}
return m
return M
}
func say_it (message, array) {