type my_class = {
  a : int;
  b : int;
  c : int;
}

let make_my_class (a : int) (b : int) (c : int) : my_class =
  { a = a; b = b; c = c }

let compute (obj : my_class) (d : int) : int =
  obj.a * d + obj.b + obj.c

(* Prove that this function always returns a positive value *)
let david_function (a : int) (b : int) : int =
  if a > 0 then
    a * 100
  else if b < 0 then
    b * -20
  else
    101

(* Prove that the following function always returns 2 * x where x is the input *)
let difficult_function (a : int) : int =
  a * 2

let handle_very_negative_case (a : int) : int option =
  if a < -100 then
    if a > -25 then
      Some (-123)
    else
      None
  else
    None

let handle_small_positive_case (a : int) : int option =
  if a < 10 then
    Some (a + 200)
  else
    None

let handle_default_case () : int =
  350

(* Decompose this *)
let other_function (a : int) : int option =
  match handle_very_negative_case a with
  | Some result -> Some result
  | None ->
    match handle_small_positive_case a with
    | Some result -> Some result
    | None -> Some (handle_default_case ())

(* Decompose this *)
let other_function2 (b : int) : int option =
  match handle_very_negative_case b with
  | Some result -> Some result
  | None ->
    match handle_small_positive_case b with
    | Some result -> Some result
    | None -> Some (handle_default_case ())

(* Decompose this *)
let other_function3 (b : int) : int option =
  match handle_very_negative_case b with
  | Some result -> Some result
  | None ->
    match handle_small_positive_case b with
    | Some result -> Some result
    | None -> Some (handle_default_case ())

(* Decompose this *)
let other_function4 (b : int) : int option =
  match handle_very_negative_case b with
  | Some result -> Some result
  | None ->
    match handle_small_positive_case b with
    | Some result -> Some result
    | None -> Some (handle_default_case ())

(* HELLLLO *)

let main () : unit =
  ()
