When you use a function as a value, F# does not give you any guarantees that the two created objects will be the "same". Under the cover the compiler creates a new closure object for each instance, so you will actually get false
as the result even when you try something like this:
balance.GetType().FullName = balance.GetType().FullName
This is the intended behavior - when you try comparing functions directly, the compiler will tell you that functions do not satisfy the equality constraint and cannot be compared:
> let balance ing gas = ing - gas;;
val balance : ing:int -> gas:int -> int
> balance = balance;;
error FS0001: The type '(int -> int -> int)' does not support the
'equality' constraint because it is a function type
This means that the best answer to your question is that what you're asking for cannot be done. I think that comparing function values is most likely not a good idea, but perhaps there is a better answer for your specific problem if you provide some more details why you want to do this.
If you really want to perform equality testing on function values, then probably the cleanest approach is to define an interface and test ordinary object equality:
type IFunction =
abstract Invoke : int * int -> int
let wrap f =
{ new IFunction with
member x.Invoke(a, b) = f a b }
Now you can wrap the balance
function in an interface implementation that can be compared:
let balance ing gas = ing - gas
let f1 = wrap balance
let f2 = f1
let f3 = wrap balance
f1 = f2 // These two are the same object and are equal
f1 = f3 // These two are different instances and are not equal