List.iter & List.fold_right used together - ocaml

I am trying to use the fold_right and List.iter functions in the List module. Is there anyway to use them in conjunction with one another?
let step nfa start transition =
let transition_list = get_transition nfa in
List.iter ( fun state ->
List.fold_right (fun ct nl ->
if ((get_pre_trans transition)= state && (get_trans ct) = transition) then
(get_post_transition transition)::nl
else
nl
) transition_list []
) start
;;
** The get_xxx functions get values from a tuple where there is a pre-transition, transition value, and post-transition.
Return error:
Error: This expression has type 'a list but an expression was expected of type unit.
Not sure what to do.

The body of the function that you pass to iter contains only one expression, a call to fold_right, that evaluates to a value of type list, but iter signature requires you to pass a function, that returns a value of type unit. That is basically what compiler tries to say to you. If you're not interested in the value to which fold_right is evaluated, then you can ignore it using ignore function, that takes a value of any type and returns a value of type unit. On the other hand, if you don't want to discard it, then you shouldn't use iter, and use fold_right or, better, fold_left.
And, finally, answering your question, yes, there're ways to combine them together, but usually, if you're applying a fold inside iter, you're doing something wrong.

Related

Function that converts a sequence to a list in OCaml

I want to convert a sequence to a list using List.init. I want at each step to retrieve the i th value of s.
let to_list s =
let n = length s in
List.init n
(fun _i ->
match s () with
| Nil -> assert false
| Cons (a, sr) -> a)
This is giving me a list initialized with the first element of s only. Is it possible in OCaml to initialize the list with all the values of s?
It may help to study the definition of List.init.
There are two variations depending on the size of the list: a tail recursive one, init_tailrec_aux, whose result is in reverse order, and a basic one, init_aux. They have identical results, so we need only look at init_aux:
let rec init_aux i n f =
if i >= n then []
else
let r = f i in
r :: init_aux (i+1) n f
This function recursively increments a counter i until it reaches a limit n. For each value of the counter that is strictly less than the limit, it adds the value given by f i to the head of the list being produced.
The question now is, what does your anonymous function do when called with different values of i?:
let f_anon =
(fun _i -> match s () with
|Nil -> assert false
|Cons(a, sr) -> a)
Regardless of _i, it always gives the head of the list produced by s (), and if s () always returns the same list, then f_anon 0 = f_anon 1 = f_anon 2 = f_anon 3 = hd (s ()).
Jeffrey Scofield's answer describes a technique for giving a different value at each _i, and I agree with his suggestion that List.init is not the best solution for this problem.
The essence of the problem is that you're not saving sr, which would let you retrieve the next element of the sequence.
However, the slightly larger problem is that List.init passes only an int as an argument to the initialization function. So even if you did keep track of sr, there's no way it can be passed to your initialization function.
You can do what you want using the impure parts of OCaml. E.g., you could save sr in a global reference variable at each step and retrieve it in the next call to the initialization function. However, this is really quite a cumbersome way to produce your list.
I would suggest not using List.init. You can write a straightforward recursive function to do what you want. (If you care about tail recursion, you can write a slightly less straightforward function.)
using a recursive function will increase the complexity so i think that initializing directly the list (or array) at the corresponding length will be better but i don't really know how to get a different value at each _i like Jeffrey Scofield said i am not really familiar with ocaml especially sequences so i have some difficulties doing that:(

How do I avoid the Value Restriction error when the argument is an empty list?

Some functions in the List module fail when the argument is an empty list. List.rev is an example. The problem is the dreaded Value Restriction.
I met the same problem while trying to define a function that returns a list with all but the last element of a list:
let takeAllButLast (xs: 'a list) =
xs |> List.take (xs.Length - 1)
The function works well with nonempty lists, but a version that would handle empty lists fails:
let takeAllButLast (xs: 'a list) =
if List.isEmpty xs then []
else xs |> List.take (xs.Length - 1)
takeAllButLast []
error FS0030: Value restriction. The value 'it' has been inferred to have generic type
val it : '_a list, etc.
I tried several things: making it an inline function, not specifying a type for the argument, specifying a type for the returned value, making the function depend on a type argument, and using the Option type to obtain an intermediate result later converted to list<'a>. Nothing worked.
For example, this function has the same problem:
let takeAllButLast<'a> (xs: 'a list) =
let empty : 'a list = []
if List.isEmpty xs then empty
else xs |> List.take (xs.Length - 1)
A similar question was asked before in SO: F# value restriction in empty list but the only answer also fails when the argument is an empty list.
Is there a way to write a function that handles both empty and nonempty lists?
Note: The question is not specific to a function that returns all but the last element of a list.
The function itself is completely fine. The function does not "fail".
You do not need to modify the body of the function. It is correct.
The problem is only with the way you're trying to call the function: takeAllButLast []. Here, the compiler doesn't know what type the result should have. Should it be string list? Or should it be int list? Maybe bool list? No way for the compiler to know. So it complains.
In order to compile such call, you need to help the compiler out: just tell it what type you expect to get. This can be done either from context:
// The compiler gleans the result type from the type of receiving variable `l`
let l: int list = takeAllButLast []
// Here, the compiler gleans the type from what function `f` expects:
let f (l: int list) = printfn "The list: %A" l
f (takeAllButLast [])
Or you can declare the type of the call expression directly:
(takeAllButLast [] : int list)
Or you can declare the type of the function, and then call it:
(takeAllButLast : int list -> int list) []
You can also do this in two steps:
let takeAllButLast_Int : int list -> int list = takeAllButLast
takeAllButLast_Int []
In every case the principle is the same: the compiler needs to know from somewhere what type you expect here.
Alternatively, you can give it a name and make that name generic:
let x<'a> = takeAllButLast [] : 'a list
Such value can be accessed as if it was a regular value, but behind the scenes it is compiled as a parameterless generic function, which means that every access to it will result in execution of its body. This is how List.empty and similar "generic values" are implemented in the standard library.
But of course, if you try to evaluate such value in F# interactive, you'll face the very same gotcha again - the type must be known - and you'll have to work around it anyway:
> x // value restriction
> (x : int list) // works

Avoid the warning "Warning 21: this statement never returns (or has an unsound type.)"

This is the first time that I met the following warning "Warning 21: this statement never returns (or has an unsound type.)" and I don't have an idea how to fix it.
let display_committers_stats response = match response##readyState with
| XmlHttpRequest.DONE ->
begin match response##status with
| 200 ->
Js_client_ui.create_menu_tabs "GitSearchTabs";
let l =
Json_parser.get_commits (Js.to_string response##responseText) in
let values =
Json_parser.group_commits_by_user l
|> List.map (fun (author, commits) ->
Js_data.create_discreteBar_item author (float_of_int commits))
|> Array.of_list
|> Js.array in
let discreteBar_chart =
Js_data.create_discreteBar_chart "Commits-impact" values in
let js_arr = Js.array ([|discreteBar_chart |]) in
Js.Unsafe.fun_call
(Js.Unsafe.variable "create_discreteBar_chart")
[|
Js.Unsafe.inject ((js_arr))
|];
let js_arr =
l
|> List.mapi (fun i commit ->
Js_data.create_timeline_data i commit.Git_data.message
commit.Git_data.time)
|> Array.of_list
|> Js.array in
Js.Unsafe.fun_call
(Js.Unsafe.variable "create_timeline")
[|
Js.Unsafe.inject ((js_arr))
|]
| _ -> Printf.printf "Unexcepted status\n" end
| _ -> Printf.printf "Unexcepted state\n"
The warning show the following line :
Js.Unsafe.fun_call
(Js.Unsafe.variable "create_discreteBar_chart")
[|
Js.Unsafe.inject ((js_arr))
|];
For execute multiples expressions in Ocaml, I know that the issue is to use ; between the expressions but what's is wrong in my function now ? Can I have some tips ?
Try wrapping the call in ignore, i.e. instead of Js.Unsafe.fun_call ...;, ignore (Js.Unsafe.fun_call ...);.
The reason this is happening is because your JS function call has a result type "'b", which is not dependent on any of the argument types. In the OCaml type system, this typically means that the function doesn't return, because the only way to "produce" a value of an arbitrary type 'b from nothing is to raise an exception – that is, to give up trying to produce it.
The sequence expression (semicolon) e1; e2 means complete the first expression, then complete the second one. In this case, OCaml is worried that your e1 (the JS function call) won't complete because of its unconstrained result type, as explained above. That would make the sequence expression pointless, which is why you get the warning. However, we know that the reason e1 has an unconstrained result type isn't because it doesn't complete, but because we are using an unsafe binding to JS.
To get around this, wrap e1 in a call to ignore, which is a function that takes anything and evaluates to unit. Now, ; will "see" unit on its left instead of an unconstrained 'b.
Generally speaking, you always want to have an expression of type unit on the left of a ;. So, even if you have an expression that evaluates to a constrained type (such as a concrete type int or a type parameter that is mentioned in the argument types), if that type is not unit, you should still wrap that expression in ignore.

function without args and return type in OCaml

First of all I usually programming in imperative languaes, that makes me hard to explain certain things. First of all is functions without args, and return types. Example is function that flattens a list:
# let rec flat = function
[] -> []
| h :: t -> h # flat t;;
val flat : 'a list list -> 'a list = <fun>
How OCaml interpreter know that:
My function flat need exactly one argument which is "list of lists".
Flat returns type is a list. Do the interpreter checks it with [] -> [] line?
let rec flat = function
[] -> []
| h :: t -> h # flat t;;
You used function keyword. function is a shortcut for match ... with. So the function you wrote is exactly like
let rec flat l =
match l with
[] -> []
| h :: t -> h # flat t
That's why ocaml knows your function has one parameter
Your function is recursive. [] -> [] is the basic case and it is also where the function will be stopped. And yes, interpreter checks it with [] -> [].
Furthermore, a function must have at least a unit parameter which is () or a normal parameter. If a function does not have anything, it is not a function, instead, it is a variable with a fixed value.
Let's have an example:
let f1 = Random.int 10;
f1 does not have any parameter, even without a () (here () is just like a method in Java without any parameter). Then f1 is a constant value which was generated by the Random. No matter when you call it, f1 will always be fixed.
let f2 () = Random.int 10;
f2 is a function. And each time you call f2(), the Random inside will generate a random in and returns it.
let rec flat = function
[] -> []
| h :: t -> h # flat t;;
Let's go through this a step at a time. The function keyword, as you might expect, gives a function. The basic syntax is function | pat1 -> branch1 | pat2 -> branch2, and what you get is a function of one argument that tries to match that argument against each pattern in turn, and for the first pattern that matches the result is the corresponding branch.
So that's how we know flat is a function. Moreover, we can see that its one argument is matched against [], which is a list. So flat must be a function that takes a list. We see that if the input is [] then the output is [], so it's a function that takes a list and returns a list.
Now let's look at that second pattern. h :: t is a pattern that matches a list and creates two new variable bindings: h is the first element of the list and t is all the rest of the elements. In particular, h has whatever type the elements of the input list have.
If you look at what happens if this pattern match succeeds, h # flat t, we see the list concatenation operator # applied to h and flat t. This means that h must be a list, and must be the same kind of list as flat t. So the elements of the input list are lists, and so is the output of the function.
This gives you flat : 'a list list -> 'a list.
To answer your questions directly, flat needs exactly one argument because it is defined with the function keyword and the return values of the branches are values and not functions (if the function branches were also functions, that would meant flat could have two or more arguments). It is a list because the pattern match is against list constructors, and it is a list of lists because h is an element of the list and is used with the # operator, which requires its arguments to be lists, so the elements of the list are lists.
There are actually three reasons why the return type must be a list:
In the first branch, a list [] is returned.
In the second branch, the result of # is returned, and # returns lists
Also in the second branch, flat t is called recursively, and then given as an argument to #. Since it is an argument to #, it must be a list, and so flat must return a list.
The third bullet point is especially interesting, because it shows you that it's not just how you create values that determines their type, but how you use them as well.

Recursive function that returns all values in list (In OCaml)

I need a function that recursively returns (not prints) all values in a list with each iteration. However, every time I try programming this my function returns a list instead.
let rec elements list = match list with
| [] -> []
| h::t -> h; elements t;;
I need to use each element each time it is returned in another function that I wrote, so I need these elements one at a time, but I can't figure this part out. Any help would be appreciated.
Your function is equivalent to :
let rec elements list =
match list with
| [] -> []
| h :: t -> elements t
This happens because a ; b evaluates a (and discards the result) and then evaluates and returns b. Obviously, this is in turn equivalent to:
let elements (list : 'a list) = []
This is not a very useful function.
Before you try solving this, however, please understand that Objective Caml functions can only return one value. Returning more than one value is impossible.
There are ways to work around this limitation. One solution is to pack all the values you wish to return into a single value: a tuple or a list, usually. So, if you need to return an arbitrary number of elements, you would pack them together into a list and have the calling code process that list:
let my_function () = [ 1 ; 2; 3; 4 ] in (* Return four values *)
List.iter print_int (my_function ()) (* Print four values *)
Another less frequent solution is to provide a function and call it on every result:
let my_function action =
action 1 ;
action 2 ;
action 3 ;
action 4
in
my_function print_int
This is less flexible, but arguably faster, than returning a list : lists can be filtered, sorted, stored...
Your question is kind of confusing - you want a function that returns all the values in a list. Well the easiest way of returning a variable number of values is using a list! Are you perhaps trying to emulate Python generators? OCaml doesn't have anything similar to yield, but instead usually accomplishes the same by "passing" a function to the value (using iter, fold or map).
What you have currently written is equivalent to this in Python:
def elements(list):
if(len(list) == 0):
return []
else:
list[0]
return elements(list[1:])
If you are trying to do this:
def elements(list):
if(len(list) > 0):
yield list[0]
# this part is pretty silly but elements returns a generator
for e in elements(list[1:]):
yield e
for x in elements([1,2,3,4,5]):
dosomething(x)
The equivalent in OCaml would be like this:
List.iter dosomething [1;2;3;4;5]
If you are trying to determine if list a is a subset of list b (as I've gathered from your comments), then you can take advantage of List.mem and List.for_all:
List.for_all (fun x -> List.mem x b) a
fun x -> List.mem x b defines a function that returns true if the value x is equal to any element in (is a member of) b. List.for_all takes a function that returns a bool (in our case, the membership function we just defined) and a list. It applies that function to each element in the list. If that function returns true for every value in the list, then for_all returns true.
So what we have done is: for all elements in a, check if they are a member of b. If you are interested in how to write these functions yourself, then I suggest reading the source of list.ml, which (assuming *nix) is probably located in /usr/local/lib/ocaml or /usr/lib/ocaml.