1

I have the following function:

def get_prev_match_elos(player_id, prev_matches):
    try:
        last_match = prev_matches[-1]
        return last_match, player_id
    except IndexError:
        return

Sometimes prev_matches can be an empty list so I've added the try except block to catch an IndexError. However, I'm still getting an explicit IndexError on last_match = prev_matches[-1] when I pass an empty list instead of the except block kicking in.

I've tried replicating this function in another file and it works fine! Any ideas?

Full error:

Exception has occurred: IndexError
list index out of range
  File "C:\Users\Philip\OneDrive\Betting\Capra\Tennis\polgara\elo.py", line 145, in get_prev_match_elos
    last_match = prev_matches[-1]
  File "C:\Users\Philip\OneDrive\Betting\Capra\Tennis\polgara\elo.py", line 24, in engineer_elos
    get_prev_match_elos(player_id, prev_matches_all_surface)
  File "C:\Users\Philip\OneDrive\Betting\Capra\Tennis\polgara\updater.py", line 499, in engineer_variables
    engineer_elos(dal, p1_id, date, surface, params)
  File "C:\Users\Philip\OneDrive\Betting\Capra\Tennis\polgara\updater.py", line 99, in run_updater
    engineer_variables(dal, matches_for_engineering, params)
  File "C:\Users\Philip\OneDrive\Betting\Capra\Tennis\polgara\decorators.py", line 12, in wrapper_timer
    value = func(*args, **kwargs)
  File "C:\Users\Philip\OneDrive\Betting\Capra\Tennis\polgara\updater.py", line 72, in main
    run_updater(dal, scraper)
  File "C:\Users\Philip\OneDrive\Betting\Capra\Tennis\polgara\updater.py", line 645, in <module>
    main()
Jossy
  • 589
  • 2
  • 12
  • 36
  • 2
    Please show the error stack trace, seems like it throws somewhere else – GProst Oct 02 '20 at 00:51
  • "still getting" or "still not getting"? – tdelaney Oct 02 '20 at 00:51
  • I can't reproduce the error. – Barmar Oct 02 '20 at 00:51
  • Check your code it's probably an issue somewhere else. – monkut Oct 02 '20 at 00:52
  • @tdelaney - sorry I wasn't clear. Will amend the post – Jossy Oct 02 '20 at 00:54
  • @GProst - added trace – Jossy Oct 02 '20 at 00:56
  • 2
    Why don't you just do `if len(prev_matches) == 0: return`? – Barmar Oct 02 '20 at 00:59
  • 1
    That s weird, are you sure you saved the new code..? that's the only explanation I can get. or maybe you re working on a copy of the file while executing an other one? – Pixel_teK Oct 02 '20 at 01:00
  • @Barmar - that works fine but the tutorials I've watched say try except is faster and better code... – Jossy Oct 02 '20 at 01:02
  • @Pixel_teK - you're telling me :) I'm using VS Code so pretty sure saving isn't the issue... – Jossy Oct 02 '20 at 01:02
  • 2
    `try/except` should be used for unusual and unexpected situations. Common situations that you can easily check for should be checked explicitly. – Barmar Oct 02 '20 at 01:03
  • 2
    And don't worry about performance unless it becomes a bottleneck. – Barmar Oct 02 '20 at 01:04
  • 1
    I'm almost positive that you're running the wrong version of the code; the fact that it works in a fresh environment is a strong clue. Do the line numbers in the stack trace line up with the numbers in your editor where you're working on this? Do the filesystem paths match exactly? – Samwise Oct 02 '20 at 01:30
  • I think that catching the exception is fine. The "unexpected situations" rule is more about the interface you expose to others. And its quite debatable where and how it is implemented. This is all in the opinion side of things. – tdelaney Oct 02 '20 at 01:31

1 Answers1

2

I also can't replicate the error, but an easy fix is to not use Exceptions this way. Programming languages aren't optimized for manually handling exceptions often. They should only be used for preemptively capturing possible failures, not for normal logic. Try checking if it's empty instead.

def get_prev_match_elos(player_id, prev_matches):
    if not prev_matches:
        return

    last_match = prev_matches[-1]
    return last_match, player_id

Here's Microsoft's take, using C# as the language:

wjandrea
  • 28,235
  • 9
  • 60
  • 81
Pieter Svenson
  • 171
  • 1
  • 9
  • 2
    I disagree. Python even has an acronym for using the try/exception coding style. EAFP. Even iteration in python is stopped by throwing a StopIteration exception. What applies to other languages doesn't necessarily apply to Python – Frank Yellin Oct 02 '20 at 01:19