func Test_ind02(tst *testing.T) { //verbose() chk.PrintTitle("ind02. copy into") rnd.Init(0) nbases := 1 A := get_individual(0, nbases) B := get_individual(1, nbases) fmts := map[string][]string{ "int": {"%2d", "%4d", "%5d"}, // ints "flt": {"%6g", "%6g", "%5g"}, // floats "str": {"%4s", "%2s", "%2s"}, // strings "key": {"%3x", "%3x", "%3x"}, // keys "byt": {"%4s", "%4s", "%4s"}, // bytes "fun": {"%3s", "%3s", "%3s"}, // funcs } io.Pfpink("A = %v\n", A.Output(fmts, false)) io.Pfcyan("B = %v\n", B.Output(fmts, false)) var ops OpsData ops.SetDefault() ops.Pc = 1.0 ops.Cuts = []int{1, 2} ops.Xrange = [][]float64{{0, 1}, {-20, 20}, {-300, 300}} a := A.GetCopy() b := A.GetCopy() IndCrossover(a, b, A, B, 0, &ops) io.Pforan("a = %v\n", a.Output(fmts, false)) io.Pfblue2("b = %v\n", b.Output(fmts, false)) chk.Ints(tst, "a.Ints ", a.Ints, []int{1, -20, 300}) chk.Ints(tst, "b.Ints ", b.Ints, []int{-1, 20, -300}) chk.Strings(tst, "a.Strings", a.Strings, []string{"abc", "Y", "c"}) chk.Strings(tst, "b.Strings", b.Strings, []string{"X", "b", "Z"}) // TODO: add other tests here io.Pf("\n") x := get_individual(0, nbases) x.Ovas = []float64{0, 0} x.Oors = []float64{0, 0, 0} io.Pfblue2("x = %v\n", x.Output(fmts, false)) B.CopyInto(x) chk.Scalar(tst, "ova0", 1e-17, x.Ovas[0], 200) chk.Scalar(tst, "ova1", 1e-17, x.Ovas[1], 100) chk.Scalar(tst, "oor0", 1e-17, x.Oors[0], 15) chk.Scalar(tst, "oor1", 1e-17, x.Oors[1], 25) chk.Scalar(tst, "oor2", 1e-17, x.Oors[2], 35) io.Pforan("x = %v\n", x.Output(fmts, false)) chk.String(tst, x.Output(fmts, false), B.Output(fmts, false)) }
func Test_pareto01(tst *testing.T) { //verbose() chk.PrintTitle("pareto01. compare vectors: Pareto-optimal") u := []float64{1, 2, 3, 4, 5, 6} v := []float64{1, 2, 3, 4, 5, 6} io.Pforan("u = %v\n", u) io.Pfblue2("v = %v\n", v) u_dominates, v_dominates := DblsParetoMin(u, v) io.Pfpink("u_dominates = %v\n", u_dominates) io.Pfpink("v_dominates = %v\n", v_dominates) if u_dominates { tst.Errorf("test failed\n") return } if v_dominates { tst.Errorf("test failed\n") return } v = []float64{1, 1.8, 3, 4, 5, 6} io.Pforan("\nu = %v\n", u) io.Pfblue2("v = %v\n", v) u_dominates, v_dominates = DblsParetoMin(u, v) io.Pfpink("u_dominates = %v\n", u_dominates) io.Pfpink("v_dominates = %v\n", v_dominates) if u_dominates { tst.Errorf("test failed\n") return } if !v_dominates { tst.Errorf("test failed\n") return } v = []float64{1, 2.1, 3, 4, 5, 6} io.Pforan("\nu = %v\n", u) io.Pfblue2("v = %v\n", v) u_dominates, v_dominates = DblsParetoMin(u, v) io.Pfpink("u_dominates = %v\n", u_dominates) io.Pfpink("v_dominates = %v\n", v_dominates) if !u_dominates { tst.Errorf("test failed\n") return } if v_dominates { tst.Errorf("test failed\n") return } }
func main() { // input data matOld := "matOld.mat" matNew := "matNew.mat" convSymb := true // parse flags flag.Parse() if len(flag.Args()) > 0 { matOld = flag.Arg(0) } if len(flag.Args()) > 1 { matNew = flag.Arg(1) } if len(flag.Args()) > 2 { convSymb = io.Atob(flag.Arg(2)) } // print input data io.Pf("\nInput data\n") io.Pf("==========\n") io.Pf(" matOld = %30s // old material filename\n", matOld) io.Pf(" matNew = %30s // new material filename\n", matNew) io.Pf(" convSymb = %30v // do convert symbols\n", convSymb) io.Pf("\n") // convert old => new inp.MatfileOld2New("", matNew, matOld, convSymb) io.Pf("conversion successful\n") io.Pfblue2("file <matNew.mat> created\n") }
func Test_GOflt01(tst *testing.T) { //verbose() chk.PrintTitle("GOflt01. float64") Init(1234) xmin := 10.0 xmax := 20.0 vals := make([]float64, NSAMPLES) // using Float64 t0 := time.Now() for i := 0; i < NSAMPLES; i++ { vals[i] = Float64(xmin, xmax) } io.Pforan("time elapsed = %v\n", time.Now().Sub(t0)) hist := Histogram{Stations: []float64{10, 12.5, 15, 17.5, 20}} hist.Count(vals, true) io.Pfpink(TextHist(hist.GenLabels("%4g"), hist.Counts, 60)) // using Float64s t0 = time.Now() Float64s(vals, xmin, xmax) io.Pforan("time elapsed = %v\n", time.Now().Sub(t0)) hist.Count(vals, true) io.Pfblue2(TextHist(hist.GenLabels("%4g"), hist.Counts, 60)) }
func main() { // default input data fn := "nurbs01.msh" ctrl := true ids := true npts := 41 // parse flags flag.Parse() if len(flag.Args()) > 0 { fn = flag.Arg(0) } if len(flag.Args()) > 1 { ctrl = io.Atob(flag.Arg(1)) } if len(flag.Args()) > 2 { ids = io.Atob(flag.Arg(2)) } if len(flag.Args()) > 3 { npts = io.Atoi(flag.Arg(3)) } // print input data io.Pforan("Input data\n") io.Pforan("==========\n") io.Pfblue2(" fn = %v\n", fn) io.Pfblue2(" ctrl = %v\n", ctrl) io.Pfblue2(" ids = %v\n", ids) io.Pfblue2(" npts = %v\n", npts) // load nurbss fnk := io.FnKey(fn) B := gm.ReadMsh(fnk) // plot plt.SetForEps(0.75, 500) for _, b := range B { if ctrl { b.DrawCtrl2d(ids, "", "") } b.DrawElems2d(npts, ids, "", "") } plt.Equal() plt.Save(fnk + ".eps") }
func Test_cxint01(tst *testing.T) { //verbose() chk.PrintTitle("cxint01") var ops OpsData ops.SetDefault() ops.Pc = 1 ops.Ncuts = 1 A := []int{1, 2} B := []int{-1, -2} a := make([]int, len(A)) b := make([]int, len(A)) IntCrossover(a, b, A, B, 0, &ops) io.Pfred("A = %2d\n", A) io.PfRed("B = %2d\n", B) io.Pfcyan("a = %2d\n", a) io.Pfblue2("b = %2d\n", b) chk.Ints(tst, "a", a, []int{1, -2}) chk.Ints(tst, "b", b, []int{-1, 2}) io.Pf("\n") A = []int{1, 2, 3, 4, 5, 6, 7, 8} B = []int{-1, -2, -3, -4, -5, -6, -7, -8} a = make([]int, len(A)) b = make([]int, len(A)) ops.Cuts = []int{1, 3} IntCrossover(a, b, A, B, 0, &ops) io.Pfred("A = %2v\n", A) io.PfRed("B = %2v\n", B) io.Pfcyan("a = %2v\n", a) io.Pfblue2("b = %2v\n", b) chk.Ints(tst, "a", a, []int{1, -2, -3, 4, 5, 6, 7, 8}) chk.Ints(tst, "b", b, []int{-1, 2, 3, -4, -5, -6, -7, -8}) ops.Cuts = []int{5, 7} IntCrossover(a, b, A, B, 0, &ops) io.Pfred("A = %2v\n", A) io.PfRed("B = %2v\n", B) io.Pfcyan("a = %2v\n", a) io.Pfblue2("b = %2v\n", b) chk.Ints(tst, "a", a, []int{1, 2, 3, 4, 5, -6, -7, 8}) chk.Ints(tst, "b", b, []int{-1, -2, -3, -4, -5, 6, 7, -8}) }
func Test_split01(tst *testing.T) { //verbose() chk.PrintTitle("split01") r := DblSplit(" 1e4 1 3 8 88 ") io.Pfblue2("r = %v\n", r) chk.Vector(tst, "r", 1e-16, r, []float64{1e4, 1, 3, 8, 88}) }
func Test_copy01(tst *testing.T) { //verbose() chk.PrintTitle("copy01") v := []float64{1, 2, 3, 4, 4, 5, 5, 6, 6, 6} w := DblCopy(v) io.Pfblue2("v = %v\n", v) chk.Vector(tst, "w==v", 1e-16, w, v) }
func Test_fileio01(tst *testing.T) { chk.PrintTitle("fileio01") // start if !Start("data/bh16.sim", true, chk.Verbose) { tst.Errorf("test failed\n") } defer End() // domain A distr := false domA := NewDomain(Global.Sim.Regions[0], distr) if domA == nil { tst.Errorf("test failed\n") } if !domA.SetStage(0, Global.Sim.Stages[0], distr) { tst.Errorf("test failed\n") } for i, _ := range domA.Sol.Y { domA.Sol.Y[i] = float64(i) } io.Pforan("domA.Sol.Y = %v\n", domA.Sol.Y) // write file tidx := 123 if !domA.SaveSol(tidx) { tst.Errorf("test failed") return } dir, fnk := Global.Dirout, Global.Fnkey io.Pfblue2("file %v written\n", out_nod_path(dir, fnk, tidx, Global.Rank)) // domain B domB := NewDomain(Global.Sim.Regions[0], distr) if domB == nil { tst.Errorf("test failed\n") } if !domB.SetStage(0, Global.Sim.Stages[0], distr) { tst.Errorf("test failed") } io.Pfpink("domB.Sol.Y (before) = %v\n", domB.Sol.Y) // read file if !domB.ReadSol(dir, fnk, tidx) { tst.Errorf("test failed") return } io.Pfgreen("domB.Sol.Y (after) = %v\n", domB.Sol.Y) // check chk.Vector(tst, "Y", 1e-17, domA.Sol.Y, domB.Sol.Y) chk.Vector(tst, "dy/dt", 1e-17, domA.Sol.Dydt, domB.Sol.Dydt) chk.Vector(tst, "d²y/dt²", 1e-17, domA.Sol.D2ydt2, domB.Sol.D2ydt2) }
func save_file(filename string, buf *bytes.Buffer, verbose bool) (err error) { fil, err := os.Create(filename) if err != nil { return } defer func() { err = fil.Close() }() _, err = fil.Write(buf.Bytes()) if verbose { io.Pfblue2("file <%s> written\n", filename) } return }
func Test_eigenp01(tst *testing.T) { //verbose() chk.PrintTitle("eigenp01") // constants tolP := 1e-14 // eigenprojectors tolS := 1e-13 // spectral decomposition toldP := 1e-9 // derivatives of eigenprojectors ver := chk.Verbose // check P verbose verdP := chk.Verbose // check dPda verbose // run test nd := test_nd for idxA := 0; idxA < len(test_nd); idxA++ { //for idxA := 10; idxA < 11; idxA++ { //for idxA := 11; idxA < 12; idxA++ { //for idxA := 12; idxA < 13; idxA++ { // tensor and eigenvalues A := test_AA[idxA] a := M_Alloc2(nd[idxA]) Ten2Man(a, A) io.PfYel("\n\ntst # %d ###################################################################################\n", idxA) io.Pfblue2("a = %v\n", a) io.Pfblue2("λ = %v\n", test_λ[idxA]) // check eigenprojectors io.Pforan("\neigenprojectors\n") λsorted := CheckEigenprojs(a, tolP, tolS, ver) io.Pfyel("λsorted = %v\n", λsorted) λchk := utl.DblGetSorted(test_λ[idxA]) chk.Vector(tst, "λchk", 1e-12, λsorted, λchk) // check derivatives of eigenprojectors io.Pforan("\nderivatives\n") CheckEigenprojsDerivs(a, toldP, verdP, EV_ZERO) } }
func Test_mat02(tst *testing.T) { chk.PrintTitle("mat02 (conversion)") convertsymbols := true MatfileOld2New("/tmp/gofem/inp", "new_layers.mat", "data/old_layers.mat", convertsymbols) mdb := ReadMat("/tmp/gofem/inp/", "new_layers.mat") if mdb == nil { tst.Errorf("test failed\n") return } io.Pfblue2("%v\n", mdb) }
func Test_hyperelast02(tst *testing.T) { //verbose() chk.PrintTitle("hyperelast02 (linear)") E, ν := 1500.0, 0.25 K := Calc_K_from_Enu(E, ν) G := Calc_G_from_Enu(E, ν) io.Pforan("K = %v\n", K) io.Pforan("G = %v\n", G) var m HyperElast1 m.Init(2, false, []*fun.Prm{ &fun.Prm{N: "K0", V: K}, &fun.Prm{N: "G0", V: G}, &fun.Prm{N: "le", V: 1}, }) io.Pforan("m = %+v\n", m) ε := []float64{-0.001, -0.002, -0.003} σ := make([]float64, 3) m.L_update(σ, ε) io.Pfblue2("ε = %v\n", ε) io.Pfcyan("σ = %v\n", σ) D := la.MatAlloc(3, 3) m.L_CalcD(D, ε) la.PrintMat("D", D, "%14.6f", false) tol := 1e-11 verb := io.Verbose var tmp float64 for i := 0; i < 3; i++ { for j := 0; j < 3; j++ { dnum := num.DerivCen(func(x float64, args ...interface{}) (res float64) { tmp, ε[j] = ε[j], x m.L_update(σ, ε) res = σ[i] ε[j] = tmp return }, ε[j]) chk.AnaNum(tst, io.Sf("D%d%d", i, j), tol, D[i][j], dnum, verb) } } }
func Test_hyperelast03(tst *testing.T) { //verbose() chk.PrintTitle("hyperelast03 (nonlinear)") var m HyperElast1 m.Init(2, false, []*fun.Prm{ &fun.Prm{N: "kap", V: 0.05}, &fun.Prm{N: "kapb", V: 20.0}, &fun.Prm{N: "G0", V: 1500}, &fun.Prm{N: "pr", V: 2.2}, &fun.Prm{N: "pt", V: 11.0}, }) io.Pforan("m = %+v\n", m) ε := []float64{-0.001, -0.002, -0.003} σ := make([]float64, 3) m.L_update(σ, ε) io.Pfblue2("ε = %v\n", ε) io.Pfcyan("σ = %v\n", σ) D := la.MatAlloc(3, 3) m.L_CalcD(D, ε) la.PrintMat("D", D, "%14.6f", false) tol := 1e-7 verb := io.Verbose var tmp float64 for i := 0; i < 3; i++ { for j := 0; j < 3; j++ { dnum := num.DerivCen(func(x float64, args ...interface{}) (res float64) { tmp, ε[j] = ε[j], x m.L_update(σ, ε) res = σ[i] ε[j] = tmp return }, ε[j]) chk.AnaNum(tst, io.Sf("D%d%d", i, j), tol, D[i][j], dnum, verb) } } }
func Test_mat01(tst *testing.T) { chk.PrintTitle("mat01") mdb1 := ReadMat("data", "bh.mat") if mdb1 == nil { tst.Errorf("test failed\n") return } io.Pforan("bh.mat just read:\n%v\n", mdb1) fn := "test_bh.mat" io.WriteFileSD("/tmp/gofem/inp", fn, mdb1.String()) mdb2 := ReadMat("/tmp/gofem/inp/", fn) if mdb2 == nil { tst.Errorf("test failed\n") return } io.Pfblue2("\n%v\n", mdb2) }
func Test_linipm03(tst *testing.T) { //verbose() chk.PrintTitle("linipm03") t0 := time.Now() defer func() { io.Pfblue2("\ntime elapsed = %v\n", time.Now().Sub(t0)) }() // read LP A, b, c, l, u := ReadLPfortran("data/afiro.dat") //A, b, c, l, u := ReadLPfortran("data/adlittle.dat") //A, b, c, l, u := ReadLPfortran("data/share1b.dat") // check for unbounded variables nx := len(c) for i := 0; i < nx; i++ { if math.Abs(l[i]) > 1e-15 { chk.Panic("cannot handle l != 0 yet") } if math.Abs(u[i]-1e20) > 1e-15 { chk.Panic("cannot handle u != ∞ yet") } } // solve LP var ipm LinIpm defer ipm.Clean() ipm.Init(A, b, c, nil) err := ipm.Solve(chk.Verbose) if err != nil { tst.Errorf("ipm failed:\n%v", err) return } // check io.Pf("\n") bres := make([]float64, len(b)) la.MatVecMul(bres, 1, A.ToDense(), ipm.X) chk.Vector(tst, "A*x=b", 1e-13, bres, b) }
func main() { // catch errors defer func() { if err := recover(); err != nil { io.PfRed("ERROR: %v\n", err) } }() // input data matOld := io.ArgToString(0, "matOld.mat") matNew := io.ArgToString(1, "matNew.mat") convSymb := io.ArgToBool(2, true) io.Pf("\n%s\n", io.ArgsTable( "old material filename", "matOld", matOld, "new material filenamen", "matNew", matNew, "do convert symbols", "convSymb", convSymb, )) // convert old => new inp.MatfileOld2New("", matNew, matOld, convSymb) io.Pf("conversion successful\n") io.Pfblue2("file <matNew.mat> created\n") }
// Run runs FE simulation func Run() (runisok bool) { // plot functions if Global.Sim.PlotF != nil && Global.Root { Global.Sim.Functions.PlotAll(Global.Sim.PlotF, Global.Dirout, Global.Fnkey) } // alloc domains var domains []*Domain for _, reg := range Global.Sim.Regions { dom := NewDomain(reg, Global.Distr) if dom == nil { break } domains = append(domains, dom) } if Stop() { return } // make sure to call linear solver clean up routines upon exit defer func() { for _, d := range domains { if !d.InitLSol { d.LinSol.Clean() } } }() // current time and output time t := 0.0 tout := 0.0 tidx := 0 // summary of outputs; e.g. with output times cputime := time.Now() var sum Summary sum.OutTimes = []float64{t} defer func() { sum.Save() if Global.Verbose && !Global.Debug { io.Pf("\nfinal t = %v\n", t) io.Pfblue2("cpu time = %v\n", time.Now().Sub(cputime)) } }() // loop over stages for stgidx, stg := range Global.Sim.Stages { // time incrementers Dt := stg.Control.DtFunc DtOut := stg.Control.DtoFunc tf := stg.Control.Tf tout = t + DtOut.F(t, nil) // set stage for _, d := range domains { if LogErrCond(!d.SetStage(stgidx, Global.Sim.Stages[stgidx], Global.Distr), "SetStage failed") { break } d.Sol.T = t if !d.Out(tidx) { break } } if Stop() { return } tidx += 1 // log models mconduct.LogModels() mreten.LogModels() mporous.LogModels() msolid.LogModels() // skip stage? if stg.Skip { continue } // time loop using Richardson's extrapolation // TODO: works with only one domain for now if Global.Sim.Solver.RE { var re RichardsonExtrap re.Init(domains[0], Dt) if !re.Run(domains[0], &sum, DtOut, &t, tf, tout, &tidx) { return } continue } // time loop ndiverg := 0 // number of steps diverging md := 1.0 // time step multiplier if divergence control is on var Δt, Δtout float64 var lasttimestep bool for t < tf { // check for continued divergence if LogErrCond(ndiverg >= Global.Sim.Solver.NdvgMax, "continuous divergence after %d steps reached", ndiverg) { return } // time increment Δt = Dt.F(t, nil) * md if t+Δt >= tf { Δt = tf - t lasttimestep = true } if Δt < Global.Sim.Solver.DtMin { if md < 1 { LogErrCond(true, "Δt increment is too small: %g < %g", Δt, Global.Sim.Solver.DtMin) return false } return true } // dynamic coefficients if LogErr(Global.DynCoefs.CalcBoth(Δt), "cannot compute dynamic coefficients") { return } // time update t += Δt for _, d := range domains { d.Sol.T = t } Δtout = DtOut.F(t, nil) // message if Global.Verbose { if !Global.Sim.Data.ShowR && !Global.Debug { io.PfWhite("%30.15f\r", t) } } // for all domains docontinue := false for _, d := range domains { // backup solution if divergence control is on if Global.Sim.Solver.DvgCtrl { d.backup() } // run iterations diverging, ok := run_iterations(t, Δt, d, &sum) if !ok { return } // restore solution and reduce time step if divergence control is on if Global.Sim.Solver.DvgCtrl { if diverging { if Global.Verbose { io.Pfred(". . . iterations diverging (%2d) . . .\n", ndiverg+1) } d.restore() t -= Δt d.Sol.T = t md *= 0.5 ndiverg += 1 docontinue = true break } ndiverg = 0 md = 1.0 } } if docontinue { continue } // perform output if t >= tout || lasttimestep { sum.OutTimes = append(sum.OutTimes, t) for _, d := range domains { //if true { if false { debug_print_p_results(d) } if false { debug_print_up_results(d) } if !d.Out(tidx) { break } } if Stop() { return } tout += Δtout tidx += 1 } } } return true }
func Test_ind03(tst *testing.T) { //verbose() chk.PrintTitle("ind03. comparing") nbases := 1 A := get_individual(0, nbases) B := get_individual(1, nbases) A_dominates, B_dominates := IndCompareDet(A, B) io.Pfblue2("A: ovas = %v\n", A.Ovas) io.Pfblue2("A: oors = %v\n", A.Oors) io.Pfcyan("B: ovas = %v\n", B.Ovas) io.Pfcyan("B: oors = %v\n", B.Oors) io.Pforan("A_dominates = %v\n", A_dominates) io.Pforan("B_dominates = %v\n", B_dominates) if !A_dominates { tst.Errorf("test failed\n") return } if B_dominates { tst.Errorf("test failed\n") return } A.Oors = []float64{0, 0, 0} B.Oors = []float64{0, 0, 0} A_dominates, B_dominates = IndCompareDet(A, B) io.Pfblue2("\nA: ovas = %v\n", A.Ovas) io.Pfblue2("A: oors = %v\n", A.Oors) io.Pfcyan("B: ovas = %v\n", B.Ovas) io.Pfcyan("B: oors = %v\n", B.Oors) io.Pforan("A_dominates = %v\n", A_dominates) io.Pforan("B_dominates = %v\n", B_dominates) if A_dominates { tst.Errorf("test failed\n") return } if B_dominates { tst.Errorf("test failed\n") return } A.Ovas = []float64{200, 100} A_dominates, B_dominates = IndCompareDet(A, B) io.Pfblue2("\nA: ovas = %v\n", A.Ovas) io.Pfblue2("A: oors = %v\n", A.Oors) io.Pfcyan("B: ovas = %v\n", B.Ovas) io.Pfcyan("B: oors = %v\n", B.Oors) io.Pforan("A_dominates = %v\n", A_dominates) io.Pforan("B_dominates = %v\n", B_dominates) if A_dominates { tst.Errorf("test failed\n") return } if B_dominates { tst.Errorf("test failed\n") return } A.Ovas = []float64{200, 99} A_dominates, B_dominates = IndCompareDet(A, B) io.Pfblue2("\nA: ovas = %v\n", A.Ovas) io.Pfblue2("A: oors = %v\n", A.Oors) io.Pfcyan("B: ovas = %v\n", B.Ovas) io.Pfcyan("B: oors = %v\n", B.Oors) io.Pforan("A_dominates = %v\n", A_dominates) io.Pforan("B_dominates = %v\n", B_dominates) if !A_dominates { tst.Errorf("test failed\n") return } if B_dominates { tst.Errorf("test failed\n") return } A.Ovas = []float64{200, 100} B.Ovas = []float64{199, 100} A_dominates, B_dominates = IndCompareDet(A, B) io.Pfblue2("\nA: ovas = %v\n", A.Ovas) io.Pfblue2("A: oors = %v\n", A.Oors) io.Pfcyan("B: ovas = %v\n", B.Ovas) io.Pfcyan("B: oors = %v\n", B.Oors) io.Pforan("A_dominates = %v\n", A_dominates) io.Pforan("B_dominates = %v\n", B_dominates) if A_dominates { tst.Errorf("test failed\n") return } if !B_dominates { tst.Errorf("test failed\n") return } }
func Test_bspline03(tst *testing.T) { //verbose() chk.PrintTitle("bspline03") // 0 1 2 3 4 5 6 7 8 9 10 T := []float64{0, 0, 0, 1, 2, 3, 4, 4, 5, 5, 5} var s Bspline s.Init(T, 2) s.SetControl([][]float64{{0, 0}, {0.5, 1}, {1, 0}, {1.5, 0}, {2, 1}, {2.5, 1}, {3, 0.5}, {3.5, 0}}) // analytical derivatives s.CalcBasisAndDerivs(3.99) io.Pfpink("ana: dNdt(t=3.99, i=5) = %v\n", s.GetDeriv(5)) io.Pfpink("ana: dNdt(t=3.99, i=6) = %v\n", s.GetDeriv(6)) io.Pfpink("ana: dNdt(t=3.99, i=7) = %v\n", s.GetDeriv(7)) s.CalcBasisAndDerivs(4.0) io.Pforan("ana: dNdt(t=4.00, i=5) = %v\n", s.GetDeriv(5)) io.Pforan("ana: dNdt(t=4.00, i=6) = %v\n", s.GetDeriv(6)) io.Pforan("ana: dNdt(t=4.00, i=7) = %v\n", s.GetDeriv(7)) // numerical derivatives io.Pfcyan("num: dNdt(t=3.99, i=5) = %v\n", s.NumericalDeriv(3.99, 5)) io.Pfcyan("num: dNdt(t=3.99, i=6) = %v\n", s.NumericalDeriv(3.99, 6)) io.Pfcyan("num: dNdt(t=3.99, i=7) = %v\n", s.NumericalDeriv(3.99, 7)) io.Pfblue2("num: dNdt(t=4.00, i=5) = %v\n", s.NumericalDeriv(4.00, 5)) io.Pfblue2("num: dNdt(t=4.00, i=6) = %v\n", s.NumericalDeriv(4.00, 6)) io.Pfblue2("num: dNdt(t=4.00, i=7) = %v\n", s.NumericalDeriv(4.00, 7)) ver := false tol := 1e-5 tt := utl.LinSpace(0, 5, 11) numd := make([]float64, s.NumBasis()) anad := make([]float64, s.NumBasis()) for _, t := range tt { for i := 0; i < s.NumBasis(); i++ { s.CalcBasisAndDerivs(t) anad[i] = s.GetDeriv(i) numd[i] = s.NumericalDeriv(t, i) // numerical fails @ 4 [4,5,6] if t == 4 { numd[4] = anad[4] numd[5] = anad[5] numd[6] = anad[6] } chk.PrintAnaNum(io.Sf("i=%d t=%v", i, t), tol, anad[i], numd[i], ver) } chk.Vector(tst, io.Sf("derivs @ %v", t), tol, numd, anad) } if chk.Verbose { npts := 201 plt.SetForPng(1.5, 600, 150) plt.SplotGap(0, 0.3) str0 := ",lw=2" str1 := ",ls='none',marker='+',color='cyan',markevery=10" str2 := ",ls='none',marker='x',markevery=10" str3 := ",ls='none',marker='+',markevery=10" str4 := ",ls='none',marker='4',markevery=10" plt.Subplot(3, 1, 1) s.Draw2d(str0, "", npts, 0) // 0 => CalcBasis s.Draw2d(str1, "", npts, 1) // 1 => RecursiveBasis plt.Subplot(3, 1, 2) s.PlotBasis("", npts, 0) // 0 => CalcBasis s.PlotBasis(str2, npts, 1) // 1 => CalcBasisAndDerivs s.PlotBasis(str3, npts, 2) // 2 => RecursiveBasis plt.Subplot(3, 1, 3) s.PlotDerivs("", npts, 0) // 0 => CalcBasisAndDerivs s.PlotDerivs(str4, npts, 1) // 1 => NumericalDeriv plt.SaveD("/tmp/gosl/gm", "bspline03.png") } }
func Test_geninvs01(tst *testing.T) { //verbose() chk.PrintTitle("geninvs01") // coefficients for smp invariants smp_a := -1.0 smp_b := 0.5 smp_β := 1e-1 // derivative values become too high with smp_ϵ := 1e-1 // small β and ϵ @ zero // constants for checking derivatives dver := chk.Verbose dtol := 1e-6 dtol2 := 1e-6 // run tests nd := test_nd for idxA := 0; idxA < len(test_nd); idxA++ { //for idxA := 10; idxA < 11; idxA++ { // tensor and eigenvalues A := test_AA[idxA] a := M_Alloc2(nd[idxA]) Ten2Man(a, A) L := make([]float64, 3) M_EigenValsNum(L, a) // SMP derivs and SMP director dndL := la.MatAlloc(3, 3) dNdL := make([]float64, 3) d2ndLdL := utl.Deep3alloc(3, 3, 3) N := make([]float64, 3) F := make([]float64, 3) G := make([]float64, 3) m := SmpDerivs1(dndL, dNdL, N, F, G, L, smp_a, smp_b, smp_β, smp_ϵ) SmpDerivs2(d2ndLdL, L, smp_a, smp_b, smp_β, smp_ϵ, m, N, F, G, dNdL, dndL) n := make([]float64, 3) SmpUnitDirector(n, m, N) // SMP invariants p, q, err := GenInvs(L, n, smp_a) if err != nil { chk.Panic("SmpInvs failed:\n%v", err) } // output io.PfYel("\n\ntst # %d ###################################################################################\n", idxA) io.Pfblue2("L = %v\n", L) io.Pforan("n = %v\n", n) io.Pforan("p = %v\n", p) io.Pforan("q = %v\n", q) // check invariants tvec := make([]float64, 3) GenTvec(tvec, L, n) proj := make([]float64, 3) // projection of tvec along n tdn := la.VecDot(tvec, n) // tvec dot n for i := 0; i < 3; i++ { proj[i] = tdn * n[i] } norm_proj := la.VecNorm(proj) norm_tvec := la.VecNorm(tvec) q_ := GENINVSQEPS + math.Sqrt(norm_tvec*norm_tvec-norm_proj*norm_proj) io.Pforan("proj = %v\n", proj) io.Pforan("norm(proj) = %v == p\n", norm_proj) chk.Scalar(tst, "p", 1e-14, math.Abs(p), norm_proj) chk.Scalar(tst, "q", 1e-13, q, q_) // dt/dL var tmp float64 N_tmp := make([]float64, 3) n_tmp := make([]float64, 3) tvec_tmp := make([]float64, 3) dtdL := la.MatAlloc(3, 3) GenTvecDeriv1(dtdL, L, n, dndL) for i := 0; i < 3; i++ { for j := 0; j < 3; j++ { dnum, _ := num.DerivCentral(func(x float64, args ...interface{}) (res float64) { tmp, L[j] = L[j], x m_tmp := SmpDirector(N_tmp, L, smp_a, smp_b, smp_β, smp_ϵ) SmpUnitDirector(n_tmp, m_tmp, N_tmp) GenTvec(tvec_tmp, L, n_tmp) L[j] = tmp return tvec_tmp[i] }, L[j], 1e-6) chk.AnaNum(tst, io.Sf("dt/dL[%d][%d]", i, j), dtol, dtdL[i][j], dnum, dver) } } // d²t/dLdL io.Pfpink("\nd²t/dLdL\n") dNdL_tmp := make([]float64, 3) dndL_tmp := la.MatAlloc(3, 3) dtdL_tmp := la.MatAlloc(3, 3) for i := 0; i < 3; i++ { for j := 0; j < 3; j++ { for k := 0; k < 3; k++ { dnum, _ := num.DerivCentral(func(x float64, args ...interface{}) (res float64) { tmp, L[k] = L[k], x m_tmp := SmpDerivs1(dndL_tmp, dNdL_tmp, N_tmp, F, G, L, smp_a, smp_b, smp_β, smp_ϵ) SmpUnitDirector(n_tmp, m_tmp, N_tmp) GenTvecDeriv1(dtdL_tmp, L, n_tmp, dndL_tmp) L[k] = tmp return dtdL_tmp[i][j] }, L[k], 1e-6) dana := GenTvecDeriv2(i, j, k, L, dndL, d2ndLdL[i][j][k]) chk.AnaNum(tst, io.Sf("d²t[%d]/dL[%d]dL[%d]", i, j, k), dtol2, dana, dnum, dver) } } } // change tolerance dtol_tmp := dtol switch idxA { case 5, 11: dtol = 1e-5 case 12: dtol = 0.0013 } // first order derivatives dpdL := make([]float64, 3) dqdL := make([]float64, 3) p_, q_, err := GenInvsDeriv1(dpdL, dqdL, L, n, dndL, smp_a) if err != nil { chk.Panic("%v", err) } chk.Scalar(tst, "p", 1e-17, p, p_) chk.Scalar(tst, "q", 1e-17, q, q_) var ptmp, qtmp float64 io.Pfpink("\ndp/dL\n") for j := 0; j < 3; j++ { dnum, _ := num.DerivCentral(func(x float64, args ...interface{}) (res float64) { tmp, L[j] = L[j], x m_tmp := SmpDirector(N_tmp, L, smp_a, smp_b, smp_β, smp_ϵ) SmpUnitDirector(n_tmp, m_tmp, N_tmp) ptmp, _, err = GenInvs(L, n_tmp, smp_a) if err != nil { chk.Panic("DerivCentral: SmpInvs failed:\n%v", err) } L[j] = tmp return ptmp }, L[j], 1e-6) chk.AnaNum(tst, io.Sf("dp/dL[%d]", j), dtol, dpdL[j], dnum, dver) } io.Pfpink("\ndq/dL\n") for j := 0; j < 3; j++ { dnum, _ := num.DerivCentral(func(x float64, args ...interface{}) (res float64) { tmp, L[j] = L[j], x m_tmp := SmpDirector(N_tmp, L, smp_a, smp_b, smp_β, smp_ϵ) SmpUnitDirector(n_tmp, m_tmp, N_tmp) _, qtmp, err = GenInvs(L, n_tmp, smp_a) if err != nil { chk.Panic("DerivCentral: SmpInvs failed:\n%v", err) } L[j] = tmp return qtmp }, L[j], 1e-6) chk.AnaNum(tst, io.Sf("dq/dL[%d]", j), dtol, dqdL[j], dnum, dver) } // recover tolerance dtol = dtol_tmp // change tolerance io.Pforan("dtol2 = %v\n", dtol2) dtol2_tmp := dtol2 switch idxA { case 5: dtol2 = 1e-5 case 10: dtol2 = 0.72 case 11: dtol2 = 1e-5 case 12: dtol2 = 544 } // second order derivatives dpdL_tmp := make([]float64, 3) dqdL_tmp := make([]float64, 3) d2pdLdL := la.MatAlloc(3, 3) d2qdLdL := la.MatAlloc(3, 3) GenInvsDeriv2(d2pdLdL, d2qdLdL, L, n, dpdL, dqdL, p, q, dndL, d2ndLdL, smp_a) io.Pfpink("\nd²p/dLdL\n") for i := 0; i < 3; i++ { for j := 0; j < 3; j++ { dnum, _ := num.DerivCentral(func(x float64, args ...interface{}) (res float64) { tmp, L[j] = L[j], x m_tmp := SmpDerivs1(dndL_tmp, dNdL_tmp, N_tmp, F, G, L, smp_a, smp_b, smp_β, smp_ϵ) SmpUnitDirector(n_tmp, m_tmp, N_tmp) GenInvsDeriv1(dpdL_tmp, dqdL_tmp, L, n_tmp, dndL_tmp, smp_a) L[j] = tmp return dpdL_tmp[i] }, L[j], 1e-6) chk.AnaNum(tst, io.Sf("d²p/dL[%d][%d]", i, j), dtol2, d2pdLdL[i][j], dnum, dver) } } io.Pfpink("\nd²q/dLdL\n") for i := 0; i < 3; i++ { for j := 0; j < 3; j++ { dnum, _ := num.DerivCentral(func(x float64, args ...interface{}) (res float64) { tmp, L[j] = L[j], x m_tmp := SmpDerivs1(dndL_tmp, dNdL_tmp, N_tmp, F, G, L, smp_a, smp_b, smp_β, smp_ϵ) SmpUnitDirector(n_tmp, m_tmp, N_tmp) GenInvsDeriv1(dpdL_tmp, dqdL_tmp, L, n_tmp, dndL_tmp, smp_a) L[j] = tmp return dqdL_tmp[i] }, L[j], 1e-6) chk.AnaNum(tst, io.Sf("d²q/dL[%d][%d]", i, j), dtol2, d2qdLdL[i][j], dnum, dver) } } // recover tolerance dtol2 = dtol2_tmp } }
func Test_ops02(tst *testing.T) { //verbose() chk.PrintTitle("ops02") nd := []int{2, 2, 3, 3, 3} AA := [][][]float64{ { {1, 2, 0}, {2, -2, 0}, {0, 0, -2}, }, { {-100, 33, 0}, {33, -200, 0}, {0, 0, 150}, }, { {1, 2, 4}, {2, -2, 3}, {4, 3, -2}, }, { {-100, -10, 20}, {-10, -200, 15}, {20, 15, -300}, }, { {-100, 0, -10}, {0, -200, 0}, {-10, 0, 100}, }, } BB := [][][]float64{ { {0.13, 1.2, 0}, {1.2, -20, 0}, {0, 0, -28}, }, { {-10, 3.3, 0}, {3.3, -2, 0}, {0, 0, 1.5}, }, { {0.1, 0.2, 0.8}, {0.2, -1.3, 0.3}, {0.8, 0.3, -0.2}, }, { {-10, -1, 2}, {-1, -20, 1}, {2, 1, -30}, }, { {-10, 3, -1}, {3, -20, 1}, {-1, 1, 10}, }, } nonsymTol := 1e-15 for m := 0; m < len(nd); m++ { // tensors A := AA[m] B := BB[m] a := M_Alloc2(nd[m]) b := M_Alloc2(nd[m]) Ten2Man(a, A) Ten2Man(b, B) io.PfYel("\n\ntst # %d ###################################################################################\n", m) io.Pfblue2("a = %v\n", a) io.Pfblue2("b = %v\n", b) // dyadic c := M_Dy(a, b) c_ := M_Alloc4(nd[m]) c__ := M_Alloc4(nd[m]) M_DyAdd(c_, 1, a, b) for i := 0; i < len(a); i++ { for j := 0; j < len(a); j++ { for k := 0; k < len(a); k++ { c__[i][j] = a[i] * b[j] } } } chk.Matrix(tst, "a dy b", 1e-12, c, c_) chk.Matrix(tst, "a dy b", 1e-12, c, c__) // dot product d := M_Alloc2(nd[m]) D := Alloc2() for i := 0; i < 3; i++ { for j := 0; j < 3; j++ { for k := 0; k < 3; k++ { D[i][j] += A[i][k] * B[k][j] } } } err := M_Dot(d, a, b, nonsymTol) for i := 0; i < 3; i++ { chk.Scalar(tst, io.Sf("a_dot_b[%d][%d]", i, i), 1e-15, D[i][i], d[i]) } /* for k := 0; k < 2*nd[m]; k++ { I, J := M2Ti[k], M2Tj[k] cf := 1.0 if k > 2 { cf = 1.0 / SQ2 } io.Pforan("%v %v\n", D[I][J], d[k] * cf) chk.Scalar(tst, io.Sf("a_dot_b[%d][%d]",I,J), 1e-15, D[I][J], d[k] * cf) } */ if err == nil { chk.Panic("dot product failed: error should be non-nil, since the result is expected to be non-symmetric") } // dot product (square tensor) a2 := M_Alloc2(nd[m]) M_Sq(a2, a) aa := M_Alloc2(nd[m]) tol_tmp := nonsymTol if m == 3 || m == 4 { nonsymTol = 1e-12 } err = M_Dot(aa, a, a, nonsymTol) io.Pforan("a2 = %v\n", a2) io.Pforan("aa = %v\n", aa) if err != nil { chk.Panic("%v", err) } chk.Vector(tst, "a2", 1e-15, a2, aa) nonsymTol = tol_tmp } }
func Test_ops03(tst *testing.T) { //verbose() chk.PrintTitle("ops03") nonsymTol := 1e-15 dtol := 1e-9 dver := chk.Verbose nd := test_nd for idxA := 0; idxA < len(test_nd)-3; idxA++ { //for idxA := 0; idxA < 1; idxA++ { // tensor and eigenvalues A := test_AA[idxA] a := M_Alloc2(nd[idxA]) Ten2Man(a, A) io.PfYel("\n\ntst # %d ###################################################################################\n", idxA) io.Pfblue2("a = %v\n", a) // inverse Ai := Alloc2() ai := M_Alloc2(nd[idxA]) detA, err := Inv(Ai, A) if err != nil { chk.Panic("%v", err) } deta_ := M_Det(a) deta, err := M_Inv(ai, a, MINDET) if err != nil { chk.Panic("%v", err) } Ai_ := Alloc2() Man2Ten(Ai_, ai) aia := M_Alloc2(nd[idxA]) err = M_Dot(aia, ai, a, nonsymTol) if err != nil { chk.Panic("%v", err) } chk.Scalar(tst, "detA", 1e-14, detA, deta) chk.Scalar(tst, "deta", 1e-14, deta, deta_) chk.Matrix(tst, "Ai", 1e-14, Ai, Ai_) chk.Vector(tst, "ai*a", 1e-15, aia, Im[:2*nd[idxA]]) io.Pforan("ai*a = %v\n", aia) // derivative of inverse dtol_tmp := dtol if idxA == 5 { dtol = 1e-8 } var tmp float64 ai_tmp := M_Alloc2(nd[idxA]) daida := M_Alloc4(nd[idxA]) M_InvDeriv(daida, ai) io.Pforan("ai = %v\n", ai) for i := 0; i < len(a); i++ { for j := 0; j < len(a); j++ { //dnum, _ := num.DerivForward(func(x float64, args ...interface{}) (res float64) { dnum, _ := num.DerivCentral(func(x float64, args ...interface{}) (res float64) { tmp, a[j] = a[j], x _, err := M_Inv(ai_tmp, a, MINDET) a[j] = tmp if err != nil { chk.Panic("daida failed:\n%v", err) } return ai_tmp[i] }, a[j], 1e-6) chk.AnaNum(tst, io.Sf("dai/da[%d][%d]", i, j), dtol, daida[i][j], dnum, dver) } } dtol = dtol_tmp } }
func Test_isofun01(tst *testing.T) { //verbose() chk.PrintTitle("isofun01. rounded cone") // SMP director parameters // Note: // 1) eps and ϵ have an effect on how close to DP/MC SMP will be // 2) as eps increases, SMP is closer to DP/MC // 3) as ϵ increases, SMP is closer to DP/MC // 4) eps also changes the shape of FC surface a, b, eps, ϵ := -1.0, 0.5, 1e-3, 1e-3 shift := 1.0 // radius r := 2.0 // failure crit parameters and number of stress components φ, ncp := 30.0, 6 // q/p coefficient μ := SmpCalcμ(φ, a, b, eps, ϵ) io.Pforan("μ = %v\n", μ) // isotropic functions var o IsoFun o.Init(a, b, eps, ϵ, shift, ncp, rounded_cone_ffcn, rounded_cone_gfcn, rounded_cone_hfcn) // plot if false { //if true { σcCte := 10.0 M := Phi2M(φ, "oct") rmin, rmax := 0.0, 1.28*M*σcCte nr, nα := 31, 81 //nr, nα := 31, 1001 npolarc := true simplec := true only0 := true grads := false showpts := false ferr := 10.0 PlotOct("fig_isofun01.png", σcCte, rmin, rmax, nr, nα, φ, o.Fa, o.Ga, npolarc, simplec, only0, grads, showpts, true, true, ferr, r, μ) } // 3D view if false { //if true { grads := true gftol := 5e-2 o.View(10, nil, grads, gftol, func(e *vtk.IsoSurf) { e.Nlevels = 7 }, r, μ) } // constants ver := chk.Verbose tol := 1e-6 tol2 := 1e-6 tolq := tol2 // check gradients for idxA := 0; idxA < len(test_nd); idxA++ { //for idxA := 0; idxA < 1; idxA++ { //for idxA := 2; idxA < 3; idxA++ { //for idxA := 10; idxA < 11; idxA++ { //for idxA := 11; idxA < 12; idxA++ { //for idxA := 12; idxA < 13; idxA++ { // tensor AA := test_AA[idxA] A := M_Alloc2(3) Ten2Man(A, AA) io.PfYel("\n\ntst # %d ###################################################################################\n", idxA) io.Pfblue2("A = %v\n", A) // function evaluation and shifted eigenvalues fval, err := o.Fa(A, r, μ) if err != nil { chk.Panic("cannot compute F(A):\n%v", err) } io.Pfpink("shift = %v\n", shift) io.Pforan("p, q = %v, %v\n", o.p, o.q) io.Pforan("f(A) = %v\n", fval) // change tolerances tol3 := tol2 tol2_tmp := tol2 switch idxA { case 7: tolq = 1e-5 case 10: tolq = 2508 // TODO tol3 = 0.772 // TODO: check why test # 10 fails with d2f/dAdA case 11: tol2 = 0.0442 // TODO: check this tol3 = 440 //TODO: check this case 12: tol2 = 1e-3 tol3 = 0.082 // TODO: check this } // check gradients err = o.CheckDerivs(A, tol, tol2, tolq, tol3, ver, r, μ) if err != nil { // plot if true { np := 41 pmin, pmax := -o.p*10, o.p*10 pq_point := []float64{o.p, o.q} o.PlotFfcn("/tmp", io.Sf("t_isofun01_%d.png", idxA), pmin, pmax, np, pq_point, "", "'ro'", nil, nil, r, μ) } // test failed chk.Panic("CheckDerivs failed:%v\n", err) } // recover tolerances tol2 = tol2_tmp } }
func Test_ops01(tst *testing.T) { //verbose() chk.PrintTitle("ops01") // basic derivatives dver := chk.Verbose dtol := 1e-5 // invariants derivatives dveri := false dtoli1 := []float64{1e-6, 1e-6, 1e-6, 1e-6, 1e-6, 1e-6, 1e-6, 1e-6, 1e-6, 1e-6} dtoli2 := []float64{1e-6, 1e-5, 1e-6, 1e-4, 1e-5, 1e-6, 1e-6, 1e-6, 1e-6, 1e-6} dtoli3 := []float64{1e-6, 1e-3, 1e-6, 1e-3, 1e-3, 1e-6, 1e-6, 1e-6, 1e-5, 1e-6} // lode derivatives dverw := chk.Verbose dtolw := 1e-8 nd := test_nd for m := 0; m < len(test_nd)-3; m++ { //for m := 0; m < 3; m++ { A := test_AA[m] a := M_Alloc2(nd[m]) Ten2Man(a, A) trA := Tr(A) tra := M_Tr(a) detA := Det(A) deta := M_Det(a) devA := Dev(A) deva := M_Dev(a) devA_ := Alloc2() a2 := M_Alloc2(nd[m]) A2 := Alloc2() A2_ := Alloc2() trDevA := Tr(devA) deva__ := M_Alloc2(nd[m]) devA__ := Alloc2() s2 := M_Alloc2(nd[m]) M_Sq(a2, a) M_Sq(s2, deva) Man2Ten(A2, a2) Man2Ten(devA_, deva) for i := 0; i < 3; i++ { for j := 0; j < 3; j++ { for k := 0; k < 3; k++ { A2_[i][j] += A[i][k] * A[k][j] } } } for i := 0; i < len(a); i++ { for j := 0; j < len(a); j++ { deva__[i] += Psd[i][j] * a[j] } } for i := 0; i < 3; i++ { for j := 0; j < 3; j++ { for k := 0; k < 3; k++ { for l := 0; l < 3; l++ { devA__[i][j] += M2TT(Psd, i, j, k, l) * A[k][l] } } } } // check basic if math.Abs(trA-tra) > 1e-17 { chk.Panic("tra failed. diff = %g", trA-tra) } if math.Abs(detA-deta) > 1e-14 { chk.Panic("detA failed. diff = %g", detA-deta) } if math.Abs(trDevA) > 1e-13 { chk.Panic("trDevA failed. error = %g", trDevA) } chk.Matrix(tst, "devA", 1e-13, devA, devA_) chk.Matrix(tst, "devA", 1e-13, devA, devA__) chk.Vector(tst, "devA", 1e-13, deva, deva__) chk.Matrix(tst, "A²", 1e-11, A2, A2_) // check tr(s2) io.Pfblue2("tr(s²) = %v\n", M_Tr(s2)) if M_Tr(s2) < 1 { chk.Panic("Tr(s2) failed") } // check derivatives da2da := M_Alloc4(nd[m]) a2tmp := M_Alloc2(nd[m]) // a2tmp == a² M_SqDeriv(da2da, a) var tmp float64 for i := 0; i < len(a); i++ { for j := 0; j < len(a); j++ { dnum, _ := num.DerivCentral(func(x float64, args ...interface{}) (res float64) { tmp, a[j] = a[j], x M_Sq(a2tmp, a) a[j] = tmp return a2tmp[i] }, a[j], 1e-6) chk.AnaNum(tst, io.Sf("da²/da[%d][%d]", i, j), dtol, da2da[i][j], dnum, dver) } } // characteristic invariants I1, I2, I3 := M_CharInvs(a) I2a := 0.5 * (tra*tra - M_Tr(a2)) I1_, I2_, I3_, dI1da, dI2da, dI3da := M_CharInvsAndDerivs(a) if math.Abs(I1-tra) > 1e-17 { chk.Panic("I1 failed (a). error = %v", I1-tra) } if math.Abs(I2-I2a) > 1e-12 { chk.Panic("I2 failed (a). error = %v (I2=%v, I2_=%v)", I2-I2a, I2, I2a) } if math.Abs(I3-deta) > 1e-17 { chk.Panic("I3 failed (a). error = %v", I3-deta) } if math.Abs(I1-I1_) > 1e-17 { chk.Panic("I1 failed (b). error = %v", I1-I1_) } if math.Abs(I2-I2_) > 1e-17 { chk.Panic("I2 failed (b). error = %v", I2-I2_) } if math.Abs(I3-I3_) > 1e-17 { chk.Panic("I3 failed (b). error = %v", I3-I3_) } // dI1da for j := 0; j < len(a); j++ { dnum, _ := num.DerivCentral(func(x float64, args ...interface{}) (res float64) { tmp, a[j] = a[j], x i1, _, _ := M_CharInvs(a) a[j] = tmp return i1 }, a[j], 1e-6) chk.AnaNum(tst, io.Sf("dI1/da[%d]", j), dtoli1[m], dI1da[j], dnum, dveri) } // dI2da for j := 0; j < len(a); j++ { dnum, _ := num.DerivCentral(func(x float64, args ...interface{}) (res float64) { tmp, a[j] = a[j], x _, i2, _ := M_CharInvs(a) a[j] = tmp return i2 }, a[j], 1e-6) chk.AnaNum(tst, io.Sf("dI2/da[%d]", j), dtoli2[m], dI2da[j], dnum, dveri) } // dI3da for j := 0; j < len(a); j++ { dnum, _ := num.DerivCentral(func(x float64, args ...interface{}) (res float64) { tmp, a[j] = a[j], x _, _, i3 := M_CharInvs(a) a[j] = tmp return i3 }, a[j], 1e-6) chk.AnaNum(tst, io.Sf("dI3/da[%d]", j), dtoli3[m], dI3da[j], dnum, dveri) } // dDet(a)/da DdetaDa := make([]float64, len(a)) M_DetDeriv(DdetaDa, a) for j := 0; j < len(a); j++ { chk.AnaNum(tst, io.Sf("dDet(a)/da[%d]", j), dtoli3[m], dI3da[j], DdetaDa[j], dveri) } // lode angle if true { s := M_Alloc2(nd[m]) dwda := M_Alloc2(nd[m]) dwda_ := M_Alloc2(nd[m]) d2wdada := M_Alloc4(nd[m]) p, q, w := M_pqws(s, a) M_LodeDeriv1(dwda, a, s, p, q, w) M_LodeDeriv2(d2wdada, dwda_, a, s, p, q, w) chk.Vector(tst, "s", 1e-13, deva, s) chk.Vector(tst, "dwda", 1e-13, dwda, dwda_) // dwda for j := 0; j < len(a); j++ { dnum, _ := num.DerivCentral(func(x float64, args ...interface{}) (res float64) { tmp, a[j] = a[j], x res = M_w(a) a[j] = tmp return res }, a[j], 1e-6) chk.AnaNum(tst, io.Sf("dw/da[%d]", j), dtolw, dwda[j], dnum, dverw) } // d2wdada s_tmp := M_Alloc2(nd[m]) dwda_tmp := M_Alloc2(nd[m]) for i := 0; i < len(a); i++ { for j := 0; j < len(a); j++ { dnum, _ := num.DerivCentral(func(x float64, args ...interface{}) (res float64) { tmp, a[j] = a[j], x p_tmp, q_tmp, w_tmp := M_pqws(s_tmp, a) M_LodeDeriv1(dwda_tmp, a, s_tmp, p_tmp, q_tmp, w_tmp) a[j] = tmp return dwda_tmp[i] }, a[j], 1e-6) chk.AnaNum(tst, io.Sf("d2w/dada[%d][%d]", i, j), dtolw, d2wdada[i][j], dnum, dverw) } } } } }
// Solve solves optimisation problem func (o *Optimiser) Solve() { // benchmark if o.Verbose { t0 := gotime.Now() defer func() { io.Pf("\nnfeval = %d\n", o.Nfeval) io.Pfblue2("cpu time = %v\n", gotime.Now().Sub(t0)) }() } // output if o.Output != nil { o.Output(0, o.Solutions) } // perform evolution done := make(chan int, o.Ncpu) time := 0 texc := time + o.DtExc for time < o.Tf { // run groups in parallel. up to exchange time for icpu := 0; icpu < o.Ncpu; icpu++ { go func(cpu int) { nfeval := 0 for t := time; t < texc; t++ { if cpu == 0 && o.Verbose { io.Pf("time = %10d\r", t+1) } nfeval += o.EvolveOneGroup(cpu) } done <- nfeval }(icpu) } for cpu := 0; cpu < o.Ncpu; cpu++ { o.Nfeval += <-done } // compute metrics with all solutions included o.Metrics.Compute(o.Solutions) // exchange via tournament if o.Ncpu > 1 { if o.ExcTour { for i := 0; i < o.Ncpu; i++ { j := (i + 1) % o.Ncpu I := rnd.IntGetUnique(o.Groups[i].Indices, 2) J := rnd.IntGetUnique(o.Groups[j].Indices, 2) A, B := o.Groups[i].All[I[0]], o.Groups[i].All[I[1]] a, b := o.Groups[j].All[J[0]], o.Groups[j].All[J[1]] o.Tournament(A, B, a, b, o.Metrics) } } // exchange one randomly if o.ExcOne { rnd.IntGetGroups(o.cpupairs, utl.IntRange(o.Ncpu)) for _, pair := range o.cpupairs { i, j := pair[0], pair[1] n := utl.Imin(o.Groups[i].Ncur, o.Groups[j].Ncur) k := rnd.Int(0, n) A := o.Groups[i].All[k] B := o.Groups[j].All[k] B.CopyInto(o.tmp) A.CopyInto(B) o.tmp.CopyInto(A) } } } // update time variables time += o.DtExc texc += o.DtExc time = utl.Imin(time, o.Tf) texc = utl.Imin(texc, o.Tf) // output if o.Output != nil { o.Output(time, o.Solutions) } } }
func Test_mylab06(tst *testing.T) { //verbose() chk.PrintTitle("mylab06. scaling") // |dx|>0: increasing io.Pfblue2("\n|dx|>0: increasing\n") reverse := false useinds := true x := []float64{10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20} s := make([]float64, len(x)) Scaling(s, x, -2.0, 1e-16, reverse, useinds) io.Pfpink("x = %v\n", x) io.Pforan("s = %v\n", s) chk.Vector(tst, "s", 1e-15, s, LinSpace(-2, -1, len(x))) // |dx|>0: reverse io.Pfblue2("\n|dx|>0: reverse\n") reverse = true Scaling(s, x, -3.0, 1e-16, reverse, useinds) io.Pfpink("x = %v\n", x) io.Pforan("s = %v\n", s) chk.Vector(tst, "s", 1e-15, s, LinSpace(-2, -3, len(x))) // |dx|>0: increasing io.Pfblue2("\n|dx|>0: increasing (shuffled)\n") reverse = false x = []float64{11, 10, 12, 19, 15, 20, 17, 16, 18, 13, 14} Scaling(s, x, 0.0, 1e-16, reverse, useinds) io.Pfpink("x = %v\n", x) io.Pforan("s = %v\n", s) chk.Vector(tst, "s", 1e-15, s, []float64{0.1, 0.0, 0.2, 0.9, 0.5, 1.0, 0.7, 0.6, 0.8, 0.3, 0.4}) // |dx|=0: increasing (using indices) io.Pfblue2("\n|dx|=0: increasing (using indices)\n") reverse = false x = []float64{123, 123, 123, 123, 123} s = make([]float64, len(x)) Scaling(s, x, 10.0, 1e-16, reverse, useinds) io.Pfpink("x = %v\n", x) io.Pforan("s = %v\n", s) chk.Vector(tst, "s", 1e-15, s, []float64{10, 10.25, 10.5, 10.75, 11}) // |dx|=0: reverse (using indices) io.Pfblue2("\n|dx|=0: reverse (using indices)\n") reverse = true Scaling(s, x, 10.0, 1e-16, reverse, useinds) io.Pfpink("x = %v\n", x) io.Pforan("s = %v\n", s) chk.Vector(tst, "s", 1e-15, s, []float64{11, 10.75, 10.5, 10.25, 10}) // |dx|=0: increasing (not using indices) io.Pfblue2("\n|dx|=0: increasing (not using indices)\n") reverse = false useinds = false Scaling(s, x, 88.0, 1e-16, reverse, useinds) io.Pfpink("x = %v\n", x) io.Pforan("s = %v\n", s) chk.Vector(tst, "s", 1e-15, s, DblVals(len(x), 88)) // |dx|=0: reverse (not using indices) io.Pfblue2("\n|dx|=0: reverse (not using indices)\n") reverse = true Scaling(s, x, 88.0, 1e-16, reverse, useinds) io.Pfpink("x = %v\n", x) io.Pforan("s = %v\n", s) chk.Vector(tst, "s", 1e-15, s, DblVals(len(x), 88)) }
// generate_solutions generate solutions func (o *Optimiser) generate_solutions(itrial int) { // benchmark t0 := gotime.Now() var tgen, tmsh gotime.Time if o.VerbTime && itrial == 0 { defer func() { io.Pfblue2("time spent in generation of solutions = %v\n", tgen.Sub(t0)) io.Pfblue2("time spent in Delaunay triangulations = %v\n", tmsh.Sub(tgen)) io.Pfblue2("total time in generate_solutions = %v\n", gotime.Now().Sub(t0)) }() } // generate if o.GenAll { o.Generator(o.Solutions, &o.Parameters) for _, sol := range o.Solutions { o.ObjFunc(sol, 0) } } else { done := make(chan int, o.Ncpu) for icpu := 0; icpu < o.Ncpu; icpu++ { go func(cpu int) { start, endp1 := (cpu*o.Nsol)/o.Ncpu, ((cpu+1)*o.Nsol)/o.Ncpu sols := o.Solutions[start:endp1] o.Generator(sols, &o.Parameters) for _, sol := range sols { o.ObjFunc(sol, cpu) } done <- 1 }(icpu) } for cpu := 0; cpu < o.Ncpu; cpu++ { <-done } } tgen = gotime.Now() // metrics o.iova0 = -1 o.Nfeval = o.Nsol o.Metrics.Compute(o.Solutions) // meshes if o.Nflt > 1 && o.UseMesh { var err error Xi, Xj := make([]float64, o.Nsol), make([]float64, o.Nsol) o.Meshes = make([][]*Mesh, o.Nflt-1) for i := 0; i < o.Nflt-1; i++ { o.Meshes[i] = make([]*Mesh, o.Nflt) for k, s := range o.Solutions { Xi[k] = s.Flt[i] } for j := i + 1; j < o.Nflt; j++ { for k, s := range o.Solutions { Xj[k] = s.Flt[j] } o.Meshes[i][j].V, o.Meshes[i][j].C, err = tri.Delaunay(Xi, Xj, false) if err != nil { chk.Panic("Delaunay2d failed:%v\n", err) } } } } tmsh = gotime.Now() }
// Run runs optimisations func (o *SimpleFltProb) Run(verbose bool) { // benchmark if verbose { time0 := time.Now() defer func() { io.Pfblue2("\ncpu time = %v\n", time.Now().Sub(time0)) }() } // run all trials for itrial := 0; itrial < o.C.Ntrials; itrial++ { // reset populations if itrial > 0 { for id, isl := range o.Evo.Islands { isl.Pop = o.C.PopFltGen(id, o.C) isl.CalcOvs(isl.Pop, 0) isl.CalcDemeritsAndSort(isl.Pop) } } // run evolution o.Evo.Run() // results xbest := o.Evo.Best.GetFloats() o.Fcn(o.ff[0], o.gg[0], o.hh[0], xbest) // check if best is unfeasible unfeasible := false for _, g := range o.gg[0] { if g < 0 { unfeasible = true break } } for _, h := range o.hh[0] { if math.Abs(h) > o.C.Eps1 { unfeasible = true break } } // feasible results if !unfeasible { for i, x := range xbest { o.Xbest[o.Nfeasible][i] = x } o.Nfeasible++ } // message if verbose { io.Pfyel("%3d x*="+o.NumfmtX+" f="+o.NumfmtF, itrial, xbest, o.ff[0]) if unfeasible { io.Pfred(" unfeasible\n") } else { io.Pfgreen(" ok\n") } } // best populations if o.C.DoPlot { if o.Nfeasible == 1 { o.PopsBest = o.Evo.GetPopulations() } else { fcur := utl.DblCopy(o.ff[0]) o.Fcn(o.ff[0], o.gg[0], o.hh[0], o.Xbest[o.Nfeasible-1]) cur_dom, _ := utl.DblsParetoMin(fcur, o.ff[0]) if cur_dom { o.PopsBest = o.Evo.GetPopulations() } } } } }
func solve_problem(fnkey string, problem int) (opt *goga.Optimiser) { // GA parameters opt = new(goga.Optimiser) opt.Default() // options for report opt.RptFmtF = "%.4f" opt.RptFmtX = "%.3f" opt.RptFmtFdev = "%.1e" opt.RptWordF = "\\beta" opt.HistFmt = "%.2f" opt.HistNdig = 3 opt.HistDelFmin = 0.005 opt.HistDelFmax = 0.005 // FORM data var lsft LSF_T var vars rnd.Variables // simple problem or FEM sim if fnkey == "simple" { opt.Read("ga-simple.json") opt.ProbNum = problem lsft, vars = get_simple_data(opt) fnkey += io.Sf("-%d", opt.ProbNum) io.Pf("\n----------------------------------- simple problem %d --------------------------------\n", opt.ProbNum) } else { opt.Read("ga-" + fnkey + ".json") lsft, vars = get_femsim_data(opt, fnkey) io.Pf("\n----------------------------------- femsim %s --------------------------------\n", fnkey) } // set limits nx := len(vars) opt.FltMin = make([]float64, nx) opt.FltMax = make([]float64, nx) for i, dat := range vars { opt.FltMin[i] = dat.Min opt.FltMax[i] = dat.Max } // log input var buf bytes.Buffer io.Ff(&buf, "%s", opt.LogParams()) io.WriteFileVD("/tmp/gosl", fnkey+".log", &buf) // initialise distributions err := vars.Init() if err != nil { chk.Panic("cannot initialise distributions:\n%v", err) } // plot distributions if opt.PlotSet1 { io.Pf(". . . . . . . . plot distributions . . . . . . . .\n") np := 201 for i, dat := range vars { plt.SetForEps(0.75, 250) dat.PlotPdf(np, "'b-',lw=2,zorder=1000") //plt.AxisXrange(dat.Min, dat.Max) plt.SetXnticks(15) plt.SaveD("/tmp/sims", io.Sf("distr-%s-%d.eps", fnkey, i)) } return } // objective function nf := 1 var ng, nh int var fcn goga.MinProb_t var obj goga.ObjFunc_t switch opt.Strategy { // argmin_x{ β(y(x)) | lsf(x) ≤ 0 } // f ← sqrt(y dot y) // g ← -lsf(x) ≥ 0 // h ← out-of-range in case Transform fails case 0: ng, nh = 1, 1 fcn = func(f, g, h, x []float64, ξ []int, cpu int) { // original and normalised variables h[0] = 0 y, invalid := vars.Transform(x) if invalid { h[0] = 1 return } // objective value f[0] = math.Sqrt(la.VecDot(y, y)) // β // inequality constraint lsf, failed := lsft(x, cpu) g[0] = -lsf h[0] = failed } // argmin_x{ β(y(x)) | lsf(x) = 0 } // f ← sqrt(y dot y) // h0 ← lsf(x) // h1 ← out-of-range in case Transform fails case 1: ng, nh = 0, 2 fcn = func(f, g, h, x []float64, ξ []int, cpu int) { // original and normalised variables h[0], h[1] = 0, 0 y, invalid := vars.Transform(x) if invalid { h[0], h[1] = 1, 1 return } // objective value f[0] = math.Sqrt(la.VecDot(y, y)) // β // equality constraint lsf, failed := lsft(x, cpu) h[0] = lsf h[1] = failed // induce minmisation of h0 //f[0] += math.Abs(lsf) } case 2: opt.Nova = 1 opt.Noor = 2 obj = func(sol *goga.Solution, cpu int) { // clear out-of-range values sol.Oor[0] = 0 // invalid transformation or FEM failed sol.Oor[1] = 0 // g(x) ≤ 0 was violated // original and normalised variables x := sol.Flt y, invalid := vars.Transform(x) if invalid { sol.Oor[0] = goga.INF sol.Oor[1] = goga.INF return } // objective value sol.Ova[0] = math.Sqrt(la.VecDot(y, y)) // β // inequality constraint lsf, failed := lsft(x, cpu) sol.Oor[0] = failed sol.Oor[1] = fun.Ramp(lsf) } default: chk.Panic("strategy %d is not available", opt.Strategy) } // initialise optimiser opt.Init(goga.GenTrialSolutions, obj, fcn, nf, ng, nh) // solve io.Pf(". . . . . . . . running . . . . . . . .\n") opt.RunMany("", "") goga.StatF(opt, 0, true) io.Pfblue2("Tsys = %v\n", opt.SysTimeAve) // check goga.CheckFront0(opt, true) // results sols := goga.GetFeasible(opt.Solutions) if len(sols) > 0 { goga.SortByOva(sols, 0) best := sols[0] io.Pforan("x = %.6f\n", best.Flt) io.Pforan("xref = %.6f\n", opt.RptXref) io.Pforan("β = %v (%v)\n", best.Ova[0], opt.RptFref[0]) } return }