DiffFunction with custom Type

已查看 27 次
跳至第一个未读帖子

Alex Minnaar

未读,
2016年12月29日 17:06:082016/12/29
收件人 Scala Breeze
Apologies if this has been asked before but I could not find the answer anywhere.  I am trying to create a DiffFunction that I can optimize via LBFGS, but my particular use-case differs from the example shown in the quickstart tutorial in that my function requires several different input parameters that are not known apriori (so hardcoding them in the calculate function is not an option).  I am thinking that one option might be to create a case class that contains all of the required parameters and use this as the DiffFunction type.  The problem with this though is that the gradient in the return tuple must be the same type so this probably won't work (the gradient is a DenseVector).  Another option is to just concatenate all of the input parameters into one really long DenseVector which I suppose would work since the gradient should be a DenseVector as well - However this will be somewhat messy since I have a lot of parameters that are both vectors and matrices.  Is there a more elegant solution to this problem?

Thanks

  

David Hall

未读,
2016年12月30日 15:23:412016/12/30
收件人 scala-...@googlegroups.com
I usually just make a class that takes the parameters in the ctor:

case class MyFun(params: Params) extends DiffFunction[DenseVector[Double]] {
 // ...
}

Does that not work here?

On Thu, Dec 29, 2016 at 4:06 PM, Alex Minnaar <minna...@gmail.com> wrote:
Apologies if this has been asked before but I could not find the answer anywhere.  I am trying to create a DiffFunction that I can optimize via LBFGS, but my particular use-case differs from the example shown in the quickstart tutorial in that my function requires several different input parameters that are not known apriori (so hardcoding them in the calculate function is not an option).  I am thinking that one option might be to create a case class that contains all of the required parameters and use this as the DiffFunction type.  The problem with this though is that the gradient in the return tuple must be the same type so this probably won't work (the gradient is a DenseVector).  Another option is to just concatenate all of the input parameters into one really long DenseVector which I suppose would work since the gradient should be a DenseVector as well - However this will be somewhat messy since I have a lot of parameters that are both vectors and matrices.  Is there a more elegant solution to this problem?

Thanks

  

--
You received this message because you are subscribed to the Google Groups "Scala Breeze" group.
To unsubscribe from this group and stop receiving emails from it, send an email to scala-breeze+unsubscribe@googlegroups.com.
To post to this group, send email to scala-...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/scala-breeze/0891d95c-3141-4634-b71f-e899312fb105%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Alex Minnaar

未读,
2016年12月30日 17:02:282016/12/30
收件人 Scala Breeze
Great idea! This works.  The only minor cosmetic issue now is that since all my parameters are passed into the class constructor I don't necessarily need to pass anything into the `calculate` method - but I can just pass in an empty DenseVector so not a big deal.  Thanks!


On Friday, December 30, 2016 at 3:23:41 PM UTC-5, David Hall wrote:
I usually just make a class that takes the parameters in the ctor:

case class MyFun(params: Params) extends DiffFunction[DenseVector[Double]] {
 // ...
}

Does that not work here?
On Thu, Dec 29, 2016 at 4:06 PM, Alex Minnaar <minna...@gmail.com> wrote:
Apologies if this has been asked before but I could not find the answer anywhere.  I am trying to create a DiffFunction that I can optimize via LBFGS, but my particular use-case differs from the example shown in the quickstart tutorial in that my function requires several different input parameters that are not known apriori (so hardcoding them in the calculate function is not an option).  I am thinking that one option might be to create a case class that contains all of the required parameters and use this as the DiffFunction type.  The problem with this though is that the gradient in the return tuple must be the same type so this probably won't work (the gradient is a DenseVector).  Another option is to just concatenate all of the input parameters into one really long DenseVector which I suppose would work since the gradient should be a DenseVector as well - However this will be somewhat messy since I have a lot of parameters that are both vectors and matrices.  Is there a more elegant solution to this problem?

Thanks

  

--
You received this message because you are subscribed to the Google Groups "Scala Breeze" group.
To unsubscribe from this group and stop receiving emails from it, send an email to scala-breeze...@googlegroups.com.

David Hall

未读,
2016年12月30日 17:40:132016/12/30
收件人 scala-...@googlegroups.com
wait, i'm very confused... if you don't have any parameters you're calculating the gradient on, then why do you need to implement the DiffFunction interface at all?

To unsubscribe from this group and stop receiving emails from it, send an email to scala-breeze+unsubscribe@googlegroups.com.

To post to this group, send email to scala-...@googlegroups.com.

Alex Minnaar

未读,
2016年12月30日 18:18:272016/12/30
收件人 Scala Breeze
To clarify, this is what its looking like now

  case class myFunc(params: Params) extends DiffFunction[DenseVector[Double]] {

    def calculate(x: DenseVector[Double]) = {

      val value =...  //uses params to calculate value
      val gradient =...  //uses params to calculate gradient

      (value, gradient)
    }
  }

 So the gradient calculation uses `params` but it doesn't use `x`.  But I think `x` still needs to be there because it needs to be the same type as the gradient (i.e. DenseVector[Double]) unless I am misunderstanding something. 



On Friday, December 30, 2016 at 5:40:13 PM UTC-5, David Hall wrote:
wait, i'm very confused... if you don't have any parameters you're calculating the gradient on, then why do you need to implement the DiffFunction interface at all?
On Fri, Dec 30, 2016 at 4:02 PM, Alex Minnaar <minna...@gmail.com> wrote:
Great idea! This works.  The only minor cosmetic issue now is that since all my parameters are passed into the class constructor I don't necessarily need to pass anything into the `calculate` method - but I can just pass in an empty DenseVector so not a big deal.  Thanks!

On Friday, December 30, 2016 at 3:23:41 PM UTC-5, David Hall wrote:
I usually just make a class that takes the parameters in the ctor:

case class MyFun(params: Params) extends DiffFunction[DenseVector[Double]] {
 // ...
}

Does that not work here?

On Thu, Dec 29, 2016 at 4:06 PM, Alex Minnaar <minna...@gmail.com> wrote:
Apologies if this has been asked before but I could not find the answer anywhere.  I am trying to create a DiffFunction that I can optimize via LBFGS, but my particular use-case differs from the example shown in the quickstart tutorial in that my function requires several different input parameters that are not known apriori (so hardcoding them in the calculate function is not an option).  I am thinking that one option might be to create a case class that contains all of the required parameters and use this as the DiffFunction type.  The problem with this though is that the gradient in the return tuple must be the same type so this probably won't work (the gradient is a DenseVector).  Another option is to just concatenate all of the input parameters into one really long DenseVector which I suppose would work since the gradient should be a DenseVector as well - However this will be somewhat messy since I have a lot of parameters that are both vectors and matrices.  Is there a more elegant solution to this problem?

Thanks

  

--
You received this message because you are subscribed to the Google Groups "Scala Breeze" group.
To unsubscribe from this group and stop receiving emails from it, send an email to scala-breeze...@googlegroups.com.
To post to this group, send email to scala-...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/scala-breeze/0891d95c-3141-4634-b71f-e899312fb105%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

--
You received this message because you are subscribed to the Google Groups "Scala Breeze" group.
To unsubscribe from this group and stop receiving emails from it, send an email to scala-breeze...@googlegroups.com.
To post to this group, send email to scala-...@googlegroups.com.

Debasish Das

未读,
2017年1月2日 19:55:462017/1/2
收件人 Scala Breeze
Hi Alex,

x for you the current assignment of the variables by the solver. Say we started with a random initialization point x = [0.2, 0.3]

You are solving for f(x) = xy - 2x

Based on this you have to find out the function value and next gradient

At given point x = [0.2, 0.3], value is a function of param and 0.2*0.3 - 2*0.2

Similarly the gradient will be df/dx = y df/dy = x At this point the gradient will be [0.3, 0.2]

Based on these, solver will find the next step: x_next = [0.2 + delta_x, 0.3 + delta_y]

So basically you will write the logic to calculate function value and gradient using x at any given solver iteration..

Alex Minnaar

未读,
2017年1月2日 21:37:192017/1/2
收件人 Scala Breeze
Thanks Debasish,  it looks like you are describing the standard case where x is a DenseVector.  My Question is what if x is something more complicated like a case class with a DenseVector and a DenseMatrix?  So basically I would want to do something like

case class Param(z: DenseVector[Double],y:DenseMatrix[Double])


val f= new DiffFunction[Param] {
 
 
def calculate(x: Param) = {
   
   
val v:Double = ... //some function of x that returns double
    val g:DenseVector[Double] = ...//some function of x that returns DenseVector[Double]

    (v, g)
 
}

}


However this will not work since x is of type Param and the gradient is of type DenseVector[Double].  So basically I am trying to figure out how to use the optimizer in this case.  Any help would be appreciated.  Thanks!

David Hall

未读,
2017年1月2日 21:48:042017/1/2
收件人 scala-...@googlegroups.com
Ah, now I think I understand. generally I pack/unpack things into a DenseVector, sometimes with a wrapping class.

To unsubscribe from this group and stop receiving emails from it, send an email to scala-breeze+unsubscribe@googlegroups.com.

To post to this group, send email to scala-...@googlegroups.com.

Alex Minnaar

未读,
2017年1月2日 22:15:442017/1/2
收件人 Scala Breeze
Thanks that sounds like a good solution
回复全部
回复作者
转发
0 个新帖子