Skip to content

Latest commit

 

History

History
45 lines (34 loc) · 1.42 KB

p0043.md

File metadata and controls

45 lines (34 loc) · 1.42 KB

[<] [^] | [>]

Problem 43: Sub-string Divisibility

The link to the problem

My approach

This problem can be solved easily by hand. In computer programming, it is enough to simply assemble numbers from the lower digits and check divisibility.

The following an example using deep-first search in OCaml.

let solve () =
  let check_divisibility s =
    let divs = [|17; 13; 11; 7; 5; 3; 2|] in
    int_of_string (String.sub s 0 3) mod divs.(String.length s - 3) = 0
  in
  let make_next_str pand_str unused_str_lst =
    List.map (fun elm -> (elm ^ pand_str, List.filter (fun s -> s <> elm) unused_str_lst))
             unused_str_lst
  in
  let rec aux = function
    | x, [] -> int_of_string x
    | x, lst when String.length x < 3 || check_divisibility x ->
	List.fold_left (+) 0 (List.map aux (make_next_str x lst))
    | _, _ -> 0    (* Divisibility check failed, so no need to look further. *)
  in
  aux ("", ["0"; "1"; "2"; "3"; "4"; "5"; "6"; "7"; "8"; "9"])

If we can use list comprehension such as Python, we can also do the following. It is a little trick to divide by 1 where no divisibility check is required.

lst = ['']
for d in [1, 1, 17, 13, 11, 7, 5, 3, 2, 1]:
    lst = [x + s for x in '0123456789' for s in lst if (x not in s) and int((x + s)[:3]) % d == 0]

print(sum(map(int, lst)))