Finding whether 2 indices are adjacent in circular list

Question:

Say I have a circular list which would look like this to a human:

enter image description here

How can I determine whether two indices are adjacent please?

So far I have:

def is_next_to(a, b):
    if a == b:
        return False
    return abs(a - b) == 1
    
    
assert is_next_to(1, 1) is False
assert is_next_to(1, 2) is True
assert is_next_to(0, 1) is True
assert is_next_to(5, 0) is True
assert is_next_to(4, 3) is True
assert is_next_to(3, 4) is True

Do I need to make special cases for (0, 5) or (5, 0), or is there some way to use modular arithmetic to solve this?

Asked By: Robin Andrews

||

Answers:

In a circle of 6, the number 5 is a neighbor of 0, but in a circle of 8, the number 5 would not be a neighbor of 0. So you can only reliable determine this when you know the size of the circle: this should be an extra parameter to your function.

Once you have that, you can use this:

def is_next_to(n, a, b):
    return abs(a - b) == 1 or a + b == n - 1

    
n = 6    
assert is_next_to(n, 1, 1) is False
assert is_next_to(n, 1, 2) is True
assert is_next_to(n, 0, 1) is True
assert is_next_to(n, 5, 0) is True
assert is_next_to(n, 4, 3) is True
assert is_next_to(n, 3, 4) is True

With modular arithmetic it would look like this:

    return (a + 1) % n == b or (b + 1) % n == a 

or:

    return (a - b) % n in (1, n - 1) 
Answered By: trincot