Advent of Code Day 2

Part 1


 Rule 1: Gradual Changes
Each pair of consecutive numbers in the report should differ by at least 1 and no more than 3.
For example, [1, 2, 3] is fine, but [1, 5] is not because the jump is too big.

Rule 2: Consistent Direction
The numbers in the report must either:
Keep increasing (or stay the same, like [1, 2, 2, 3]), or
Keep decreasing (like [5, 4, 3, 2]).

Dampener (for Part Two)
If a report is not safe by the above rules, we’re allowed to remove one number and check again.
For example, if [1, 3, 2, 4] isn’t safe, removing 3 gives [1, 2, 4], which might be safe.
Key Examples
[7, 6, 4, 2, 1] → Safe: It keeps decreasing gradually.
[1, 2, 7, 8, 9] → Unsafe: The jump from 2 to 7 is too big.
[8, 6, 4, 4, 1] → Unsafe: The numbers stop decreasing at 4, 4.With the dampener:
[8, 6, 4, 4, 1] becomes safe if we remove the first 4.

    

Source Code

def is_safe(report):
    levels = report.split()
    int_levels = []
    for level in levels:
        int_levels.append(int(level))
    levels = int_levels

    #Increasing or decreasing
    is_increasing = True
    is_decreasing = True

for i in range(len(levels) - 1): # Time O(m)
        diff = abs(levels[i+1] - levels[i])

        if diff < 1 or diff > 3:
            return False
        
        if levels[i] >= levels[i + 1]:
            is_increasing = False
        if levels[i] <= levels[i + 1]:
            is_decreasing = False

    return is_decreasing or is_increasing

with open("src\day-2\input.txt", "r") as file:
    reports = file.readlines()

safe_count = 0
for report in reports: # Time O(n)
    if is_safe(report.strip()):
        safe_count += 1

print(safe_count)

Part 2

7 6 4 2 1: Safe without removing any level.
1 2 7 8 9: Unsafe regardless of which level is removed.
9 7 6 2 1: Unsafe regardless of which level is removed.
1 3 2 4 5: Safe by removing the second level, 3.
8 6 4 4 1: Safe by removing the third level, 4.
1 3 6 7 9: Safe without removing any level.
Step 1: Define the Rules
Rule 1: Gradual Changes
Each pair of consecutive numbers in the report must differ by at least 1 and at most 3.
Example: [1, 2, 3] is valid because the differences are 1.
Example: [1, 5] is invalid because the difference is 4.
Rule 2: Consistent Direction
The numbers must either:
Keep increasing (e.g., [1, 2, 3, 4]), or
Keep decreasing (e.g., [5, 4, 3, 2]).
Reports that switch directions, like [1, 3, 2], are not valid.
Step 2: Add the Problem Dampener (Part Two)
What is the Dampener?
If a report fails the rules, the dampener allows you to remove one number.
Then, you check again if the modified report follows the rules.
Example:
[8, 6, 4, 4, 1]:
Without the dampener: Unsafe because 4, 4 stops the decreasing pattern.
With the dampener: Safe if you remove one 4, leaving [8, 6, 4, 1].
Step 3: Plan the Solution
Function to Check Safety:

Verify if the differences between numbers are within range (1 to 3).
Ensure all numbers are either increasing or decreasing.
Function to Check Safety with the Dampener:

Try removing each number in the report one at a time.
Check if the remaining numbers follow the safety rules.
Count the Safe Reports:

Go through the list of reports and count how many are safe.
For Part Two, include reports that become safe with the dampener.

Source code

def is_safe(report):
    levels = report.split()
    int_levels = []
    for level in levels:
        int_levels.append(int(level))
    levels = int_levels

def check_safety(levels):
        #Increasing or decreasing
        is_increasing = True
        is_decreasing = True

        for i in range(len(levels) - 1): # Time O(m)
            diff = abs(levels[i+1] - levels[i])

            if diff < 1 or diff > 3:
                return False
            
            if levels[i] >= levels[i + 1]:
                is_increasing = False
            if levels[i] <= levels[i + 1]:
                is_decreasing = False

        return is_decreasing or is_increasing
    
if check_safety(levels):
        return True
    
    for i in range(len(levels)):
        modified_levels = []
        for j in range(len(levels)):
            if i != j:
                modified_levels.append(levels[j])

        if check_safety(modified_levels):
            return True

with open("src\day-2\input.txt", "r") as file:
    reports = file.readlines()

safe_count = 0
for report in reports: # Time O(n)
    if is_safe(report.strip()):
        safe_count += 1

print(safe_count)