Traffic speed limit check for intervals Given 2 lists of tuples limits and speeds, both have the format of [(speed1, time1), (speed2, time2)]. My goal is to write a function to check whether the there is a period of time that the speed exceeds the limit (Return True if exceeds).
For example, Given limits = [(50,100), (30, 20)], speeds = [(30, 80), (10, 30), (40, 10)], return True.

The example inputs imply that during the first 100 miles, the speed limit is 50. In the 101-120 mile, speed limit is 30. Since in the speeds list, the last 10 miles have speed 40 > 30, so we return True.

We can assume the inputs are valid, so the limits and speeds list always start and end at the same time.

Can I have some pointers on the correctness and how the code can be refactored?

def speed_check(limits, speeds):
  i, j = 0, 0
  prev_limit_range, prev_speed_range = 0, 0
  while j &lt; len(speeds) and i &lt; len(limits):
    if limits[i][0] &lt; speeds[j][0]:
      return True
    if limits[i][1] + prev_limit_range &lt; speeds[j][1] + prev_speed_range:
      prev_limit_range += limits[i][1]
      i += 1
    elif limits[i][1] + prev_limit_range &gt; speeds[j][1] + prev_speed_range:
      prev_speed_range += speeds[j][1]
      j += 1
    else:
      prev_limit_range += limits[i][1]
      prev_speed_range += speeds[j][1]
      i += 1
      j += 1

  return False

assert speed([(30, 15), (55, 20)], [(30, 15), (55, 20)]) == False
assert speed([(30, 15), (55, 20)], [(30, 14), (65, 20)]) == True
First, let's look at your answer with comments:

def speed_check(limits, speeds):
  # Explicit assignment of temporary variables
  i, j = 0, 0
  prev_limit_range, prev_speed_range = 0, 0
  # Assumption that speeds and limits will not change during iteration
  while j &lt; len(speeds) and i &lt; len(limits):
    # Multiple if statements make it so that we can't just swap lines of
    # code without breaking things.
    if limits[i][0] &lt; speeds[j][0]: # speed &gt; limit would be more readable
      return True
    # Operator precedence does not jump to the eye. Use parenthesis
    if limits[i][1] + prev_limit_range &lt; speeds[j][1] + prev_speed_range:
      prev_limit_range += limits[i][1]
      i += 1
    elif limits[i][1] + prev_limit_range &gt; speeds[j][1] + prev_speed_range:
      prev_speed_range += speeds[j][1]
      j += 1
    else:
    # Manual incrementation of local variables. 
      prev_limit_range += limits[i][1]
      prev_speed_range += speeds[j][1]
      i += 1
      j += 1

  return False


Python-wise there are multiple parts of your implementation that could be tackled differently. Let's see what we could do. 

If you think about this problem graphically, drawing an x-axis for distance and a y-axis for speed, then all you want is to check whether the curve for actual speed ever crosses the curve for speed limits.

You could break down your problem into subparts:

def get_graph(speedlist):
    """Generate a list of tuples into a flatten list as in:
    [(1,2), (3, 4)] -&gt; [1, 1, 3, 3, 3, 3]       
    """
    return [item for x in [y[1]*[y[0]] for y in speedlist] for item in x]

def check_exceeds(speeds, limits):
    speed_graph = get_graph(speeds)
    limits_graph = get_graph(limits)
    return any([x &gt; y for x, y in zip(speed_graph, limits_graph)])


This approach avoids three issues I see in your implementation:  excess of if-statements, explicit indexing, and explicit iteration. Why are these issues? Well, it's easy to make mistakes when indexing and manually iterating, and it's easy to forget possible branches when using if/else clauses. Python offers a lot of tooling so that you don't have to do everything yourself, and it's considered good practice to leverage that tooling to make your code both more readable and safe.

For your assertions, there is also no need to compare to True nor False, in case your function is defined in such a way that it returns a boolean: 

assert check_exceeds([(30, 15), (55, 20)], [(30, 15), (55, 20)])
assert not check_exceeds([(30, 15), (55, 20)], [(30, 14), (65, 20)])


(quick answer as I was answering the post in StackOverflow before it migrated)