···11+import fileinput
22+33+44+def is_fresh(ingredient, intervals):
55+ for a, b in intervals:
66+ if a <= ingredient <= b:
77+ return True
88+99+ return False
1010+1111+1212+def is_overlap(a, b, c, d):
1313+ """Returns the (min, max) if (a, b) and (c, d) overlap, else None."""
1414+ if a <= c <= d <= b:
1515+ return a, b
1616+ elif c <= a <= b <= d:
1717+ return c, d
1818+ elif c <= b <= d and a <= c <= b:
1919+ return a, d
2020+2121+ return None, None
2222+2323+2424+def merge_intervals(intervals):
2525+ def _merge_one_pass(intervals):
2626+ new_intervals = []
2727+2828+ for y in range(len(intervals)):
2929+ for x in range(len(intervals)):
3030+ if x == y:
3131+ continue
3232+3333+ a, b = intervals[x]
3434+ c, d = intervals[y]
3535+ m, n = is_overlap(a, b, c, d)
3636+3737+ if m is not None and n is not None:
3838+ new_intervals = [interval for i, interval in enumerate(intervals) if i != x and i != y]
3939+ new_intervals.append((m, n))
4040+ return new_intervals
4141+4242+ return intervals
4343+4444+ while True:
4545+ new_intervals = _merge_one_pass(intervals)
4646+ if len(new_intervals) == len(intervals):
4747+ return intervals
4848+ intervals = new_intervals
4949+5050+5151+# Read problem input.
5252+INTERVALS = []
5353+INGREDIENTS = []
5454+for line in fileinput.input():
5555+ line = line.strip()
5656+ if '-' in line:
5757+ a, b = line.split('-')
5858+ INTERVALS.append((int(a), int(b)))
5959+ elif line:
6060+ INGREDIENTS.append(int(line))
6161+6262+# Solve problem.
6363+INTERVALS = merge_intervals(INTERVALS)
6464+print("Part 1:", sum(is_fresh(ingredient, INTERVALS) for ingredient in INGREDIENTS))
6565+print("Part 2:", sum(b - a + 1 for a, b in INTERVALS))