# Function remove\_half

**URL:** <https://discuss.ocaml.org/t/function-remove-half/10459>\
**Category:** Learning\
**Tags:** ocaml\
**Created:** [September 12, 2022, 7:53am UTC](https://discuss.ocaml.org/t/function-remove-half/10459 "2022-09-12T07:53:32Z")\
**Posts on this page:** 7\
**Page:** 1

<div class="post-metadata">

**Author:** ![catie](https://avatars.discourse-cdn.com/v4/letter/c/ea666f/32.png) [@catie](https://discuss.ocaml.org/u/catie)\
**Post date:** [September 12, 2022, 7:53am UTC](https://discuss.ocaml.org/t/function-remove-half/10459/1 "2022-09-12T07:53:32Z")

</div>

hi everybody,

i have to write a function remove\_half l that returns one element out of two like in this exemple.  
exemple: remove\_half [‘c’ ; ‘a’ ; ‘t’ ; ‘i’ ; ‘e’];; retourne: [‘c’ ; ‘t’ ; ‘e’]\*)  
thanks in advance for all

---

<div class="post-metadata">

**Author:** ![cloudyhug](https://sea2.discourse-cdn.com/flex020/user_avatar/discuss.ocaml.org/cloudyhug/32/2399_2.png) [@cloudyhug](https://discuss.ocaml.org/u/cloudyhug)\
**Post date:** [September 12, 2022, 8:20am UTC](https://discuss.ocaml.org/t/function-remove-half/10459/2 "2022-09-12T08:20:59Z")

</div>

Hello. As in [your other post](https://discuss.ocaml.org/t/need-help-with-exercices-please/10458), I will try to give you an idea without giving the full solution.

This is a recursive function on a list. The two constructors for a list are `[]` and `::`, meaning that every list is either `[]` or `x :: xs` with `x` an element and `xs` another list.

As a first idea, you can match the input list and see what you need to do in each case:

```ocaml
let rec remove_half1 l =
  match l with
  | [] -> (* what to do in the empty case? *)
  | x :: xs -> (* what to do with x? what to do with xs? *)

```

The problem is that here you want to do a different thing with `x` according to the position in the list (even or odd). It means you need to know the position when you match on `l`, so your function must have an additional argument to remember the position.

```ocaml
let rec remove_half2 n l =
  match l with
  | [] -> (* ... *)
  | x :: xs -> if (* test on n *) then (* ... *) else (* ... *)

```

If you manage to write this `remove_half2` it will have the following type:

```ocaml
remove_half2 : int -> `a list -> `a list

```

but `remove_half` does not have this `int` parameter. It means that you need to run `remove_half2` with an initial value so that you have the right type for your final function.

```ocaml
let remove_half l = remove_half2 (* initial value *) l

```

Good luck!

---

<div class="post-metadata">

**Author:** ![catie](https://avatars.discourse-cdn.com/v4/letter/c/ea666f/32.png) [@catie](https://discuss.ocaml.org/u/catie)\
**Post date:** [September 12, 2022, 9:46am UTC](https://discuss.ocaml.org/t/function-remove-half/10459/3 "2022-09-12T09:46:16Z")

</div>

i did that 🙂 let rec remove\_half n l =  
match l with  
| →   
| x :: xs → if List.tl (List.tl l) = then [List.hd (l)] else remove\_half (List.tl l);;  
but i have an error " Error: This expression has type 'a list → 'a list  
but an expression was expected of type 'a list"

---

<div class="post-metadata">

**Author:** ![octachron](https://avatars.discourse-cdn.com/v4/letter/o/49beb7/32.png) [@octachron](https://discuss.ocaml.org/u/octachron)\
**Post date:** [September 12, 2022, 5:06pm UTC](https://discuss.ocaml.org/t/function-remove-half/10459/4 "2022-09-12T17:06:45Z")

</div>

You don’t need to use `List.tl l` nor `List.hd l` with pattern matching. In the right-hand side of

```ocaml
| x :: xs -> ... (*here*)

```

`x` is `List.hd l` and `xs` is `List.tl`.  
The type error is due to the fact that `remove_half` expect two arguments and in

```ocaml
.... else remove_half xs

```

you are only providing one argument to the function.

---

<div class="post-metadata">

**Author:** ![catie](https://avatars.discourse-cdn.com/v4/letter/c/ea666f/32.png) [@catie](https://discuss.ocaml.org/u/catie)\
**Post date:** [September 12, 2022, 5:45pm UTC](https://discuss.ocaml.org/t/function-remove-half/10459/5 "2022-09-12T17:45:17Z")

</div>

i did that but i think tat’s wrong

---

<div class="post-metadata">

**Author:** ![catie](https://avatars.discourse-cdn.com/v4/letter/c/ea666f/32.png) [@catie](https://discuss.ocaml.org/u/catie)\
**Post date:** [September 12, 2022, 5:58pm UTC](https://discuss.ocaml.org/t/function-remove-half/10459/6 "2022-09-12T17:58:15Z")

</div>

i did this one let remove\_half l =  
let rec rm\_half n l =  
if l = then   
else  
let fst = hd l in  
let rest = tl l in  
if n then fst :: (rm\_half (not n) rest) else (rm\_half (not n) rest) in  
rm\_half true l;;

but that’ s not clear for me with match with  
do you have a suggestions?

---

<div class="post-metadata">

**Author:** ![otini](https://sea2.discourse-cdn.com/flex020/user_avatar/discuss.ocaml.org/otini/32/3533_2.png) [@otini](https://discuss.ocaml.org/u/otini)\
**Post date:** [September 13, 2022, 11:57am UTC](https://discuss.ocaml.org/t/function-remove-half/10459/7 "2022-09-13T11:57:04Z")

</div>

You can make your code easier to read for us on this forum by putting between ``` marks like this:

````auto
```ocaml
Your code here
```

````

Your code works, here is a version with some simplifications and syntactic tricks to make it more “idiomatic” OCaml:

```ocaml
let rm_half l =
  let rec aux keep = function
  | [] -> []
  | hd :: tl -> if keep then hd :: aux false tl else aux true tl
  in
  aux true l

```

Namely:

- Pattern matching rather than using `List.hd` and `List.tl`
- Using the `function ... | ...` keyword, equivalent to `fun l -> match l with ... | ...`
- Using an auxiliary function and declaring it in the scope of the function that uses it, to make sure that it is not used by mistake.
