Thursday, April 16, 2015

Problem 102 - F#

So, now that I had a day of solving a ridiculous problem in a ridiculous language, now I get a chance to do a reasonable problem in a somewhat reasonable language. F# is a weird blend of a mostly functional programming language with tons of impure features and some strangeness from the fact that it runs on the CLI and thus links to the same library functions as C#. In my previous use of F#, I was able to basically treat it as a dialect of ML, but this time around I got a chance to use a number of the strange impure features. The results were interesting, and everything basically worked out, even if it was a very odd mixing of paradigms. Anyway, the problem itself wasn't too difficult after ensuring that I could do file I/O, and spending a couple of minutes thinking about how to answer "point contained in triangle" questions. The below solution runs in about 50ms:

type Point = { x : float; y : float}

let mutable ans = 0
let mutable c = 0


let ell (A : Point) (B : Point) x = 
    (B.y - A.y) / (B.x - A.x) * (x - A.x) + A.y

let isValid (points : Point[]) i =
    let A = points.[(i + 1) % 3] in
    let B = points.[(i + 2) % 3] in
    let f = ell A B in
    let p = points.[i] in
    if (A.x = B.x) then
        (p.x > A.x) = (0.0 > A.x)
    else
        (p.y - (f p.x)) * (- (f 0.0)) > 0.0

for line in System.IO.File.ReadLines("triangles.txt") do
  let rawpoints = Array.map (fun s -> System.Double.Parse(s)) (line.Split(','))
  let points = Array.map (fun i -> { x = rawpoints.[i*2]; y = rawpoints.[i*2 + 1] } : Point ) [|0 .. 2|]

  ans <- ans + (if (Array.fold (fun b i  -> b && isValid points i) true [| 0 .. 2 |]) then 1 else 0)


printfn "%d" ans

No comments:

Post a Comment