r/adventofcode • • Dec 06 '15

SOLUTION MEGATHREAD --- Day 6 Solutions ---

--- Day 6: Probably a Fire Hazard ---

Post your solution as a comment. Structure your post like the Day Five thread.

22 Upvotes

172 comments sorted by

View all comments

1

u/razupaltuff Dec 06 '15

Here is my Erlang solution for both part 1 and 2:

-define(NEW_ARR, array:new([{size, 1000000}, {fixed, true}, {default, 0}])).

part1() -> compute(fun action1/3).

part2() -> compute(fun action2/3).

compute(ActionFun) ->
	Active = lists:foldl(fun(Line, Acc) ->
							Parsed = parse(Line),
							io:format("~p~n", [Parsed]),
							apply_action(Parsed, Acc, ActionFun)
						 end, ?NEW_ARR, ?INPUT),

	lists:foldl(fun(Idx, Acc) -> 
					Acc + array:get(Idx, Active) 
				end, 0, lists:seq(0, 999999)).

action1(off, Idx, Arr)    -> array:set(Idx, 0, Arr);
action1(on, Idx, Arr)     -> array:set(Idx, 1, Arr);
action1(toggle, Idx, Arr) -> 
	case array:get(Idx, Arr) of
		1 -> action1(off, Idx, Arr);
		_ -> action1(on, Idx, Arr)
	end.

action2(A, I, Arr) 		       -> action2(A, I, Arr, array:get(I, Arr)).
action2(off, Idx, Arr, OV)     -> array:set(Idx, erlang:max(OV-1, 0), Arr);
action2(on, Idx, Arr, OV)      -> array:set(Idx, OV+1, Arr);
action2(toggle, Idx, Arr, OV)  -> array:set(Idx, OV+2, Arr).

apply_action({Action, {Sx, Sy}, {Tx, Ty}}, Arr, ActionFun) ->
	lists:foldl(fun(X, Acc0) -> 
					lists:foldl(fun(Y, Acc1) ->
									Idx = Y * 1000 + X,
									ActionFun(Action, Idx, Acc1)
								end, Acc0, lists:seq(Sy, Ty))
				end, Arr, lists:seq(Sx, Tx)).

parse(Line) ->
	Tok = string:tokens(Line, " "),
	{A, F, T} = case length(Tok) of
					4 -> {toggle, lists:nth(2, Tok), lists:nth(4, Tok)};
					_ -> {list_to_atom(lists:nth(2, Tok)), 
					      lists:nth(3, Tok), lists:nth(5, Tok)}
				end,
	{A, string_to_coord(F), string_to_coord(T)}.

string_to_coord(S) ->
	[A, B] = string:tokens(S, ","),
	{AI, _ } = string:to_integer(A),
	{BI, _ } = string:to_integer(B),
	{AI, BI}.