//gnEigen wraps the matrix.DenseMatrix.Eigen() function in order to guarantee //That the eigenvectors and eigenvalues are sorted according to the eigenvalues //It also guarantees orthonormality and handness. I don't know how many of //these are already guaranteed by Eig(). Will delete the unneeded parts //And even this whole function when sure. The main reason for this function //Is the compatibiliy with go.matrix. This function should dissapear when we //have a pure Go blas. func EigenWrap(in *Matrix, epsilon float64) (*Matrix, []float64, error) { if epsilon < 0 { epsilon = appzero } efacs := mat64.Eigen(mat64.DenseCopyOf(in.Dense), epsilon) evecsprev := &Matrix{efacs.V} evalsmat := efacs.D() d, _ := evalsmat.Dims() evals := make([]float64, d, d) for k, _ := range evals { evals[k] = evalsmat.At(k, k) } evecs := Zeros(3) fn := func() { evecs.Copy(evecsprev.T()) } err := mat64.Maybe(fn) if err != nil { return nil, nil, Error{err.Error(), []string{"mat64.Copy/math64.T", "EigenWrap"}, true} } //evecs.TCopy(evecs.Dense) eig := eigenpair{evecs, evals[:]} sort.Sort(eig) //Here I should orthonormalize vectors if needed instead of just complaining. //I think orthonormality is guaranteed by DenseMatrix.Eig() If it is, Ill delete all this //If not I'll add ortonormalization routines. eigrows, _ := eig.evecs.Dims() for i := 0; i < eigrows; i++ { vectori := eig.evecs.VecView(i) for j := i + 1; j < eigrows; j++ { vectorj := eig.evecs.VecView(j) if math.Abs(vectori.Dot(vectorj)) > epsilon && i != j { reterr := Error{fmt.Sprintln("Eigenvectors ", i, "and", j, " not orthogonal. v", i, ":", vectori, "\nv", j, ":", vectorj, "\nDot:", math.Abs(vectori.Dot(vectorj)), "eigmatrix:", eig.evecs), []string{"EigenWrap"}, true} return eig.evecs, evals[:], reterr } } if math.Abs(vectori.Norm(0)-1) > epsilon { //Of course I could just normalize the vectors instead of complaining. //err= fmt.Errorf("Vectors not normalized %s",err.Error()) } } //Checking and fixing the handness of the matrix.This if-else is Jannes idea, //I don't really know whether it works. // eig.evecs.TCopy(eig.evecs) if det(eig.evecs) < 0 { //Right now, this will fail if the matrix is not 3x3 (30/10/2013) eig.evecs.Scale(-1, eig.evecs) //SSC } else { /* eig.evecs.TransposeInPlace() eig.evecs.ScaleRow(0,-1) eig.evecs.ScaleRow(2,-1) eig.evecs.TransposeInPlace() */ } // eig.evecs.TCopy(eig.evecs) return eig.evecs, eig.evals, nil //Returns a slice of evals }
// erro no ask -> não devo passar loc.X como x func (c *CMAES) ask() []float64 { lenC, _ := c.C.Dims() if float64(c.CountEval-c.EigenEval) > float64(c.Lambda)/(c.C1+c.Cmu)/float64(lenC)/10.0 { c.EigenEval = c.CountEval c.C.Add(c.C, c.C.T()) c.C.Scale(0.5, c.C) eig := mat64.Eigen(c.C, 0.000001) // fmt.Println("here") c.D = eig.D() c.B = eig.V // fmt.Println("# Entrou no loop") // fmt.Println("# ask c.B", c.B) // fmt.Println("# ask c.D", c.D) // fmt.Println("# ask c.C", c.C) // fmt.Println("# ask c.InvSqrtC", c.InvSqrtC) // fmt.Println("# here") for i := 0; i < c.N; i++ { if c.D.At(i, i) < 0 { c.D.Set(i, i, -1*math.Sqrt(-1*c.D.At(i, i))) } else { c.D.Set(i, i, math.Sqrt(c.D.At(i, i))) } } c.InvSqrtC.Inverse(c.D) c.InvSqrtC.Mul(c.B, c.InvSqrtC) c.InvSqrtC.Mul(c.InvSqrtC, c.B.T()) // fmt.Println("Entrou no loop") // fmt.Println("ask c.B", c.B) // fmt.Println("ask c.D", c.D) // fmt.Println("ask c.C", c.C) // fmt.Println("ask c.InvSqrtC", c.InvSqrtC) } randn := make([]float64, c.N) for i := 0; i < c.N; i++ { randn[i] = c.D.At(i, i) * rand.NormFloat64() } tmp := mat64.NewDense(c.N, 1, randn) tmp.Mul(c.B, tmp) newL := make([]float64, c.N) for i := 0; i < c.N; i++ { newL[i] = c.Xmean[i] + c.Sigma*tmp.At(i, 0) } // fmt.Println("ask tmp", tmp) return newL }
func (t Tournament) Ranks() []float64 { m := t.Matrix() eig := mat64.Eigen(m, 1e-10) _, c := eig.V.Dims() var ranks []float64 for i := 0; i < c; i++ { ranks = eig.V.Col(nil, i) sense := math.Copysign(1, ranks[0]) for _, val := range ranks { if sense == 0 { sense = math.Copysign(1, val) } if val*sense < 0 { ranks = nil break } } if ranks != nil { min := 1e100 max := 0.0 for i := range ranks { col := t.Matrix().Col(nil, i) row := t.Matrix().Row(nil, i) tot := 0.0 for j := range col { tot += col[j] + row[j] } ranks[i] = ranks[i] * sense / tot // normalize to # games min = math.Min(ranks[i], min) max = math.Max(ranks[i], max) } // uncomment this to make min score = 0 and max score = 1 //for i := range ranks { // ranks[i] = (ranks[i] - min) / (max - min) //} break } } return ranks }
func main() { flag.Parse() log.SetFlags(0) var tourn Tournament if *demo { tourn = Tournament{ {"bob-r", "joe-c"}, {"bob-r", "tim-c"}, {"bob-r", "tim-c"}, {"bob-r", "tim-c"}, {"joe-r", "tim-c"}, {"joe-r", "bob-c"}, {"tim-r", "joe-c"}, {"tim-r", "bob-c"}, {"bob-c", "joe-r"}, {"bob-c", "tim-r"}, {"joe-c", "tim-r"}, {"joe-c", "bob-r"}, {"tim-c", "joe-r"}, {"tim-c", "bob-r"}, } } else { matches, err := ParseMatches(os.Stdin) if err != nil { log.Fatal(err) } tourn = Tournament(matches) } if *graph { tourn.Graph(os.Stdout) return } else if *matrix { prefix := "tournmat = " fmt.Printf("%v%v\n", prefix, mat64.Formatted(tourn.Matrix(), mat64.Prefix(strings.Repeat(" ", len(prefix))))) return } else if *eigvect { eig := mat64.Eigen(tourn.Matrix(), 1e-10) prefix := "eigvects = " fmt.Printf("%v%.4v\n", prefix, mat64.Formatted(eig.V, mat64.Prefix(strings.Repeat(" ", len(prefix))))) return } else if *eigval { eig := mat64.Eigen(tourn.Matrix(), 1e-10) prefix := "eigvals = " fmt.Printf("%v%.4v\n", prefix, mat64.Formatted(eig.D(), mat64.Prefix(strings.Repeat(" ", len(prefix))))) return } ranks := tourn.Ranks() if ranks == nil { log.Fatalf("no valid eigenvector ranking found") } players := tourn.Players() for i, rank := range ranks { fmt.Printf("%v\t%.2v\n", players[i], rank) } }