3
votes

I am writing a function to return a list minus the third value. Here is my current code:

let listString = [ "1"; "2"; "3"; "4" ];;

let del3 (listA :'a)  =  [listA.Head; listA.Tail.Head] @ [listA.Tail.Tail.Tail];;

del3 listString

and I am getting the error:

Lookup on object of indeterminate type based on information prior to this program point. A type annotation may be needed prior to this program point to constrain the type of the object. This may allow the lookup to be resolved.

What should I change to fix the error?

3
Try to avoid .Head and .Tail. - J D

3 Answers

16
votes

I think a simpler approach based on a pattern match might be better

let del3 = function |a::b::c::d -> a::b::d | _ -> failwith "insufficient input"
7
votes

You need to let the compiler know that listA is a list. Also Tail returns a list, so for the second list you're appending you don't want to wrap the tail in a list, otherwise you're going to have a list of a list:

let listString = [ "1"; "2"; "3"; "4" ]

let del3 (listA :'a list)  =  [listA.Head; listA.Tail.Head] @ listA.Tail.Tail.Tail

del3 listString;;

A solution to handle lists of all sizes:

let del3 = function
    | a::b::c::tail -> a::b::tail
    | list -> list
2
votes

When accessing members, methods or properties of an object, F# needs to know the type of that object. It can't just infer the type from the fact that you're accessing a property named Head because there might be many different classes that have such a property.

To fix this problem, either give listA a type annotation or use List.head and List.tail instead of the properties.