3
votes

I got the following error:

Error 2 Value restriction. The value 'gbmLikelihood' has been inferred to have generic type val gbmLikelihood : (float -> '_a -> float [] -> float) when '_a :> seq<float> Either make the arguments to 'gbmLikelihood' explicit or, if you do not intend for it to be generic, add a type annotation.

and this type is exactly what I want. What do I have to do to make it work, and why doesn't it just work without intervention?

EDIT:
The error comes from this file (its short, so I paste the whole lot):

module Likelihood
open System

let likelihood getDrift getVol dt data parameters =
    let m = getDrift data parameters
    let s =  getVol data parameters
    let N = float (Seq.length data)
    let sqrt_dt = Math.Sqrt dt
    let constant = -0.5*Math.Log(2.0*Math.PI*dt)*N
    let normalizedResidue observation = (observation - (m - 0.5*s*s)*dt)/(s*sqrt_dt) 
    let residueSquared observation = 
        let r = normalizedResidue observation in r*r
    let logStdDev = Math.Log s
    constant - logStdDev*N - 0.5* (data |> Seq.sumBy residueSquared) 

let gbmLikelihood = likelihood (fun data p -> Array.get p 0) (fun datac p -> Array.get p 1)
2
Can you post an example demonstrating the error?pad

2 Answers

7
votes

This error can happen when you declare a value that has a generic type. See for example this past SO question. In your case, the type suggests that you are trying to define a function, but the compiler does not see it as a syntactic function. This can happen if you perform some effects and then return function using the lambda syntax:

let wrong = 
  printfn "test"
  (fun x -> x)

To avoid the problem, you need to write the function using the function syntax:

printfn "test"
let wrong x = x

EDIT: In your concrete example, the function gbmLikelihood is created as a result of a partial function application. To make it compile, you need to turn it into an explicit function:

let gbmLikelihood parameters = 
  likelihood (fun data p -> Array.get p 0) (fun datac p -> Array.get p 1) parameters 

For more information why this is the case & how it works, see also this great article on value restriction in F#.

1
votes

Instead of making the parameters of gbmLikelihood explicit you might also just add a generic type annotation to the function:

let gbmLikelihood<'a> = 
    likelihood (fun data p -> Array.get p 0) (fun datac p -> Array.get p 1)