Types from findLargestPrimeFactor are no findLargestPrimeFactor in use. The F # compiler performs type inference on a top-down basis, so the types p and n (parameters findLargestPrimeFactor ) are inferred from their use in the function. By the time the compiler sees let result = ... , the parameter types have already been inferred as int .
The simplest solution is to use the L suffix for all of your constant values, so the types will be inferred as int64 :
let rec findLargestPrimeFactor pn = if n = 1L then p else if n % p = 0L then findLargestPrimeFactor p (n/p) else findLargestPrimeFactor (p + 1L) n let result = findLargestPrimeFactor 2L 600851475143L
If you want a better solution, you can use general and zero constants from the LanguagePrimitives module. This allows findLargestPrimeFactor be generic (-ish) so that it can be reused with different numeric types:
open LanguagePrimitives let rec findLargestPrimeFactor pn = if n = GenericOne then p else if n % p = GenericZero then findLargestPrimeFactor p (n/p) else findLargestPrimeFactor (p + GenericOne) n (* You can use one of these, but not both at the same time -- now the types of the _arguments_ are used to infer the types of 'p' and 'n'. *) //let result = findLargestPrimeFactor 2L 600851475143L let result = findLargestPrimeFactor 2 Int32.MaxValue
According to the @kvb suggestion, here you can write this function in general form:
open LanguagePrimitives let inline findLargestPrimeFactor pn = let rec findLargestPrimeFactor pn = if n = GenericOne then p else if n % p = GenericZero then findLargestPrimeFactor p (n/p) else findLargestPrimeFactor (p + GenericOne) n findLargestPrimeFactor pn (* Now you can call the function with different argument types as long as the generic constraints are satisfied. *) let result = findLargestPrimeFactor 2L 600851475143L let result' = findLargestPrimeFactor 2 Int32.MaxValue
Jack P. Feb 21 '13 at 17:41 2013-02-21 17:41
source share