Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
Show all changes
31 commits
Select commit Hold shift + click to select a range
fb74645
Initial commit and skeleton for NonlinearMinimizer
Jan 30, 2015
a7ee059
Merge branch 'qp' of https://github.com/debasish83/breeze into nlqp
Jan 31, 2015
679bb5f
Skeleton for approximate eigen value calculation
Feb 2, 2015
3d80b31
Copyright message for NonlinearMinimizer
Feb 2, 2015
3781e37
merge with qp branch; NOTICE file updated
Feb 3, 2015
536886d
Initial checkin for PowerMethod and PowerMethodTest;Eigen value extra…
Feb 3, 2015
f98bd80
Compilation fixes to LBFGS eigenMin and eigenMax
Feb 4, 2015
ae795b6
Power Method merged; NonlinearMinimizer now supports preserving histo…
Feb 11, 2015
51b4224
Generating PQN.CompactHessian from BFGS.ApproximateInverseHessian not…
Feb 11, 2015
ee697bf
Linear Regression formulation added for comparisons
Feb 11, 2015
ce8638f
Fixed LBFGS.maxEigen using power law on CompactHessian
Feb 12, 2015
bbc3edd
Merge branch 'qp' of https://github.com/debasish83/breeze into nlqp
Feb 17, 2015
f85ff86
Merge branch 'qp' of https://github.com/debasish83/breeze into nlqp
Feb 22, 2015
e3a61a9
Added a proximal interface to ProjectQuasiNewton solver; Added projec…
Feb 23, 2015
928de32
probability simplex benchmark
Feb 24, 2015
91f2e17
After experimentation NonlinearMinimizer now users PQN/OWLQN and supp…
Feb 28, 2015
33d28ff
Add testcases for Least square variants
Mar 1, 2015
6cba897
merge with upstream
Mar 1, 2015
9bef354
I dunno.
dlwh Mar 1, 2015
18c7789
PQN fixes from David's fix_pqn branch; added strong wolfe line search…
Mar 2, 2015
43794c0
Unused import from FirstOrderMinimizer; PQN migrated to Strong Wolfe …
Mar 5, 2015
e2c1db8
Used BacktrackingLineSearch in SPG and PQN; Updated NonlinearMinimize…
Mar 5, 2015
defaff5
NonlinearMinimizer println changed to nl from pqn
Mar 5, 2015
610027f
Updated with cforRange in proximal operations
Mar 7, 2015
8c6a6c8
BacktrackingLineSearch takes an initfval;OWLQN, PQN and SPG updated t…
Mar 7, 2015
b4d86e8
Merge branch 'master' of https://github.com/scalanlp/breeze into nlqp
Mar 7, 2015
3a6fc97
infiniteIteration API in FirstOrderMinimizer takes initialState;PQN b…
Mar 11, 2015
8533ada
migrate LBFGS Eigen calculation to https://github.com/debasish83/bree…
Mar 11, 2015
a0bbd33
cleaned up minEigen call from QuadraticMinimizer
Mar 11, 2015
40a45a8
NonlinearMinimizer inner iterations through BFGS cleaned
Mar 12, 2015
7308c7a
Updated contributions in README.md
Mar 12, 2015
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
Added a proximal interface to ProjectQuasiNewton solver; Added projec…
…tion operators for ProbabilitySimplex and L1; Compared PQN with OWLQN and ADMM for L1 constraint
  • Loading branch information
Debasish Das committed Feb 23, 2015
commit e3a61a9625816351d92c1b6da22e070cd1a2b58a
21 changes: 0 additions & 21 deletions math/src/main/scala/breeze/optimize/LBFGS.scala
Original file line number Diff line number Diff line change
Expand Up @@ -96,26 +96,6 @@ class LBFGS[T](maxIter: Int = -1, m: Int=10, tolerance: Double=1E-9)
logger.info(s"LBFGS Min Eigen iterations ${eigenState.iter}")
1.0/eigenState.eigenValue
}

/**
* Get the maximum approximate eigen value of the quadratic approximation convex function specified
* through DiffFunction by doing a inverse power iteration using the CompactHessian representation
* generated from ApproximateInverseHessian, get the largest eigenvalue e
*
* @param init initial guess for the eigen vector
* @param state the current state of the optimization
* @return maximum eigen value
*/
def maxEigen(state: State, init: T) : Double = {
val compactHessian = new CompactHessian(state.history.m)
val memStep = state.history.memStep.asInstanceOf[Seq[DenseVector[Double]]]
val memGradDelta = state.history.memGradDelta.asInstanceOf[Seq[DenseVector[Double]]]
(0 to state.history.historyLength - 1).map{i => compactHessian.updated(memStep(i), memGradDelta(i))}
val pm = new PowerMethod[T, CompactHessian]()(space, ProjectedQuasiNewton.multiplyCompactHessian)
val eigenState = pm.iterateAndReturnState(init, compactHessian)
logger.info(s"LBFGS Max Eigen iterations ${eigenState.iter}")
eigenState.eigenValue
}
}

object LBFGS {
Expand Down Expand Up @@ -180,6 +160,5 @@ object LBFGS {
def apply(a: ApproximateInverseHessian[T], b: T): T = a * b
}
}

}

39 changes: 27 additions & 12 deletions math/src/main/scala/breeze/optimize/ProjectedQuasiNewton.scala
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,10 @@ package breeze.optimize

import breeze.linalg._
import breeze.collection.mutable.RingBuffer
import breeze.linalg.operators.OpMulMatrix
import breeze.math.{MutableInnerProductModule}
import breeze.optimize.proximal.Constraint.Constraint
import breeze.optimize.proximal.Constraint._
import breeze.optimize.proximal._
import breeze.util.SerializableLogging

// Compact representation of an n x n Hessian, maintained via L-BFGS updates
Expand Down Expand Up @@ -84,7 +86,6 @@ class ProjectedQuasiNewton(tolerance: Double = 1e-6,

type History = CompactHessian


protected def initialHistory(f: DiffFunction[DenseVector[Double]], init: DenseVector[Double]): History = {
new CompactHessian(m)
}
Expand All @@ -109,7 +110,6 @@ class ProjectedQuasiNewton(tolerance: Double = 1e-6,
}
}


protected def determineStepSize(state: State, fn: DiffFunction[DenseVector[Double]], dir: DenseVector[Double]): Double = {
if (state.iter == 0)
return scala.math.min(1.0, 1.0 / norm(state.grad,1.0))
Expand Down Expand Up @@ -153,14 +153,12 @@ class ProjectedQuasiNewton(tolerance: Double = 1e-6,
projection(state.x + dir * stepSize)
}


protected def updateHistory(newX: DenseVector[Double], newGrad: DenseVector[Double], newVal: Double, f: DiffFunction[DenseVector[Double]], oldState: State): History = {
import oldState._
val s = newX - oldState.x
val y = newGrad - oldState.grad
val s = newX - x
val y = newGrad - grad
oldState.history.updated(y, s)
}

}

object ProjectedQuasiNewton {
Expand All @@ -186,12 +184,29 @@ object ProjectedQuasiNewton {
}
}

implicit def multiplyCompactHessian[T](implicit vspace: MutableInnerProductModule[T, Double]): OpMulMatrix.Impl2[CompactHessian, T, T] = {
new OpMulMatrix.Impl2[CompactHessian, T, T] {
def apply(a: CompactHessian, b: T): T = {
val result = a * b.asInstanceOf[DenseVector[Double]]
result.asInstanceOf[T]
case class Projection(proximal: Proximal) {
def project(x: DenseVector[Double]) : DenseVector[Double] = {
proximal.prox(x)
x
}
}

def proximal(proximal: Proximal) = new ProjectedQuasiNewton(projection = Projection(proximal).project)

def apply(ndim: Int, constraint: Constraint, lambda: Double=1.0): ProjectedQuasiNewton = {
constraint match {
case POSITIVE => proximal(ProjectPos())
case BOX => {
val lb = DenseVector.zeros[Double](ndim)
val ub = DenseVector.ones[Double](ndim)
proximal(ProjectBox(lb, ub))
}
case EQUALITY => {
val aeq = DenseVector.ones[Double](ndim)
proximal(ProjectHyperPlane(aeq, 1.0))
}
case SPARSE => proximal(ProjectL1(lambda))
case PROBABILITYSIMPLEX => proximal(ProjectProbabilitySimplex(lambda))
}
}
}
Expand Down
2 changes: 1 addition & 1 deletion math/src/main/scala/breeze/optimize/Projecting.scala
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
package breeze.optimize

import breeze.math.{Module, NormedVectorSpace}
import breeze.math.{Module}

trait Projecting[T] {
def projection: T => T
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,5 +6,5 @@ package breeze.optimize.proximal
*/
object Constraint extends Enumeration {
type Constraint = Value
val SMOOTH, POSITIVE, BOX, SPARSE, EQUALITY = Value
val SMOOTH, POSITIVE, BOX, SPARSE, EQUALITY, PROBABILITYSIMPLEX = Value
}
Loading