Browse thread
Style and organization of code
[
Home
]
[ Index:
by date
|
by threads
]
[ Message by date: previous | next ] [ Message in thread: previous | next ] [ Thread: previous | next ]
[ Message by date: previous | next ] [ Message in thread: previous | next ] [ Thread: previous | next ]
Date: | 2007-03-15 (03:44) |
From: | Chris King <colanderman@g...> |
Subject: | Re: [Caml-list] Style and organization of code |
On 3/14/07, ian <fist_187@softhome.net> wrote: > Say I have a function called "solveHardProblem". solveHardProblem relies on > several helper functions, which are not going to be useful to any other > functions in the program. So, my first instinct would be to define all the > helpers using let blocks within the definition of solveHardProblem. I usually do exactly that. I think it's fine to have a long let like this, so long as it's made up of small, manageable pieces. The biggest problem is that your arguments are now miles away from the definition of your function, but this can be solved with something like the following: let solve_hard_problem = let solve_simpler_problem x = ... and solve_something_else x = ... in fun x y z -> [code goes here] This is also a good trick for moving a global variable (such as a unique ID counter or a hash table) into the scope of the function that uses it. FWIW I've seen some examples of this style in the standard library. genlex.ml has a 150+ line function of the form: let make_lexer keywords = let kwd_table = Hashtbl.create 17 in List.iter (fun s -> Hashtbl.add kwd_table s (Kwd s)) keywords; let ident_or_keyword id = ... and keyword_or_error c = ... [snip] in fun input -> Stream.from (fun count -> next_token input) Since the "keywords" argument is needed by the helper functions, it appears at the top in the let, but "input" isn't and so it was moved to the bottom in the fun. None of the helper functions are much longer than one screenful so it makes for easy reading.