Gradient descent: Difference between revisions

Content added Content deleted
(Added a task description including some references.)
(Added Go)
Line 11: Line 11:


[https://books.google.co.uk/books?id=dFHvBQAAQBAJ&pg=PA543&lpg=PA543&dq=c%23+steepest+descent+method+to+find+minima+of+two+variable+function&source=bl&ots=TCyD-ts9ui&sig=ACfU3U306Og2fOhTjRv2Ms-BW00IhomoBg&hl=en&sa=X&ved=2ahUKEwitzrmL3aXjAhWwVRUIHSEYCU8Q6AEwCXoECAgQAQ#v=onepage&q=c%23%20steepest%20descent%20method%20to%20find%20minima%20of%20two%20variable%20function&f=false This book excerpt] shows sample C# code for solving this task.
[https://books.google.co.uk/books?id=dFHvBQAAQBAJ&pg=PA543&lpg=PA543&dq=c%23+steepest+descent+method+to+find+minima+of+two+variable+function&source=bl&ots=TCyD-ts9ui&sig=ACfU3U306Og2fOhTjRv2Ms-BW00IhomoBg&hl=en&sa=X&ved=2ahUKEwitzrmL3aXjAhWwVRUIHSEYCU8Q6AEwCXoECAgQAQ#v=onepage&q=c%23%20steepest%20descent%20method%20to%20find%20minima%20of%20two%20variable%20function&f=false This book excerpt] shows sample C# code for solving this task.
<br><br>
=={{header|Go}}==
This is a translation of the C# code in the book excerpt linked to above and hence also of the first Typescript example below.

For some unknown reason the results differ from the other solutions after the first 4 decimal places but are near enough for an approximate method such as this.
<lang go>package main

import (
"fmt"
"math"
)

func steepestDescent(x []float64, alpha, tolerance float64) {
n := len(x)
h := tolerance
g0 := g(x) // Initial estimate of result.

// Calculate initial gradient.
fi := gradG(x, h)

// Calculate initial norm.
delG := 0.0
for i := 0; i < n; i++ {
delG += fi[i] * fi[i]
}
delG = math.Sqrt(delG)
b := alpha / delG

// Iterate until value is <= tolerance.
for delG > tolerance {
// Calculate next value.
for i := 0; i < n; i++ {
x[i] -= b * fi[i]
}
h /= 2

// Calculate next gradient.
fi = gradG(x, h)

// Calculate next norm.
delG = 0
for i := 0; i < n; i++ {
delG += fi[i] * fi[i]
}
delG = math.Sqrt(delG)
b = alpha / delG

// Calculate next value.
g1 := g(x)

// Adjust parameter.
if g1 > g0 {
alpha /= 2
} else {
g0 = g1
}
}
}

// Provides a rough calculation of gradient g(x).
func gradG(x []float64, h float64) []float64 {
n := len(x)
z := make([]float64, n)
y := make([]float64, n)
copy(y, x)
g0 := g(x)

for i := 0; i < n; i++ {
y[i] += h
z[i] = (g(y) - g0) / h
}
return z
}

// Function for which minimum is to be found.
func g(x []float64) float64 {
return (x[0]-1)*(x[0]-1)*
math.Exp(-x[1]*x[1]) + x[1]*(x[1]+2)*
math.Exp(-2*x[0]*x[0])
}

func main() {
tolerance := 0.0000006
alpha := 0.1
x := []float64{0.1, -1} // Initial guess of location of minimum.

steepestDescent(x, alpha, tolerance)
fmt.Println("Testing steepest descent method:")
fmt.Println("The minimum is at x[0] =", x[0], "\b, x[1] =", x[1])
}
</lang>

{{out}}
<pre>
Testing steepest descent method:
The minimum is at x[0] = 0.10764302056464771, x[1] = -1.223351901171944
</pre>


=={{header|TypeScript}}==
=={{header|TypeScript}}==