Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

nested try/except in Python

try:
  commands
  try:
    commands
    try:
      commands
      try:
        commands
      except:
        commands
        return to final commands
    except:
      commands
      return to final commands
  except:
    commands
    return to final commands
except:
  commands

final commands

Which instruction have I to write in place of return to final commands to make that any except returns to the top-level instructions following the outer try? And is it an acceptable structure?

Edit: Here is a toy example (I know I can do it using ifs, it's only an example; suppose you have to write it using try/except).

# calculate arcsin(log(sqrt(x)-4))
x = choose one yourself
try
  x1=sqrt(x)
  return to final message
  try
    x1=log(x1-4)
    return to final message
    try
      x2=arcsin(x1)
      return to final message
    except
      message="Impossible to calculate arcsin: maybe an argument outside [-1,+1]?"
  except
    message="Impossible to calculate logarithm: maybe a not positive argument?"
except
  message="impossible to calculate square root: maybe a negative argument?" 
final message:
print message
like image 298
tic Avatar asked Nov 09 '13 21:11

tic


1 Answers

At the very least you should be able to reduce this structure to only 2 nested levels by reraising the exception to avoid the rest of the block:

# calculate arcsin(log(sqrt(x)-4))
x = ?
message = None
try:
    try:
        x1 = sqrt(x)
    except Exception:
        message = "can't take sqrt"
        raise
    try:
         x1 = log(x1-4)
    except Exception:
        message = "can't compute log"
        raise
    try:
        x2 = arcsin(x1)
    except Exception:
        message = "Can't calculate arcsin"
        raise
except Exception:
    print message

Really, this is not the way to do it, at least in this example. The problem is that you are trying to use exceptions like return error codes. What you should be doing is putting the error message into the exception. Also, normally the outer try/except would be in a higher level function:

def func():
    try:
        y = calculate_asin_log_sqrt(x)
        # stuff that depends on y goes here
    except MyError as e:
        print e.message
    # Stuff that happens whether or not the calculation fails goes here

def calculate_asin_log_sqrt(x):
    try:
        x1 = sqrt(x)
    except Exception:
        raise MyError("Can't calculate sqrt")
    try:
        x1 = log(x1-4)
    except Exception:
        raise MyError("Can't calculate log")
    try:
        x2 = arcsin(x1)
    except Exception:
        raise MyError("Can't calculate arcsin") 
    return x2
like image 165
Evan Avatar answered Oct 26 '22 16:10

Evan