2011-01-19 39 views
14

Tôi có một chút mã thực hiện xử lý ngoại lệ chức năng và mọi thứ hoạt động tốt, ngoại lệ được nâng lên khi tôi muốn, nhưng khi tôi gỡ lỗi, các dấu vết không phải lúc nào cũng làm những gì tôi muốn.Exception Passing Trong Python

Ví dụ A:

>>> 3/0 
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
ZeroDivisionError: integer division or modulo by zero 

Ví dụ B:

>>> try: 3/0 
... except Exception as e: raise e 
... 
Traceback (most recent call last): 
    File "<stdin>", line 2, in <module> 
ZeroDivisionError: integer division or modulo by zero 

Trong cả hai ví dụ, ngoại trừ thực sự xảy ra ở dòng 1, nơi mà chúng tôi cố gắng làm 3/0, nhưng trong ví dụ sau, chúng tôi được cho biết đã xảy ra trên dòng 2, nơi nó được nâng lên.

Có cách nào bằng Python để nâng cao một ngoại lệ, như thể nó là một ngoại lệ, cái gì đó sẽ cho kết quả sau:

>>> try: 3/0 
... except Exception as e: metaraise(e) 
... 
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
ZeroDivisionError: integer division or modulo by zero 

Trả lời

4

Để tham khảo, giải pháp là xấp xỉ như sau:

def getException(): 
    return sys.exc_info() 

def metaraise(exc_info): 
    raise exc_info[0], exc_info[1], exc_info[2] 

try: 3/0 
except: 
    e = getException() 
    metaraise(e) 

Phần đẹp của việc này là bạn có thể vượt qua xung quanh biến điện tử và metaraise nó ở một nơi khác , ngay cả khi các ngoại lệ khác đã gặp phải trên đường đi.

+1

Nhưng sau đó bạn sẽ không có thông tin về dấu vết của khoản tăng mới. Bất kỳ người bắt nào ở trên đều sẽ bị lừa khi tin rằng ngoại lệ chỉ được nâng lên ở vị trí ban đầu. Các raiser thứ hai giấu sự tồn tại của nó mà có thể khá khó hiểu trong các trường hợp gỡ lỗi. – Alfe

17

Khi bạn tái huy động một ngoại lệ mà bạn bắt gặp, chẳng hạn như

except Exception as e: raise e 

nó đặt lại theo dõi ngăn xếp. Nó giống như việc nâng cấp một ngoại lệ mới. Những gì bạn muốn là thế này:

except Exception as e: raise 
+1

Và bạn không cần phải lưu trữ trong một biến trong trường hợp này. –

+0

Ngoại trừ việc tôi cần phải lưu trữ nó trong một biến bằng cách nào đó và chuyển nó đến một nơi nào đó nó sẽ được nâng lên. –

+1

@Kevin Dolan: và điều này làm cho mã của bạn dễ hiểu hơn và có thể gỡ lỗi hơn, hoặc nó là một mục nhập trong một cuộc thi obfuscation? –