0

このコードを仮定すると:

connection = get_some_connection() # maybe from oursql
with connection.cursor() as cursor:
    cursor.execute('some query')

cursor.close()after finishedが自動的に実行されることを理解しています。例外はどうですか?それらを中に入れなければなりませんか?

connection = get_some_connection() # maybe from oursql
with connection.cursor() as cursor:
    try:
        cursor.execute('some query')
    except IntegrityError, e:
        # handle exceoption

または、 with ステートメントでそれらを処理するより良い方法はありますか?

4

2 に答える 2

4

with x as y: z()基本的に、次の構文糖衣です。

y = x
y.__enter__()
try:
    z()
finally:
    if y.__exit__: y.__exit__()

これは完全に正確ではありませんが、それが要点です。__exit__()例外がスローされた場合は例外情報が渡されることに注意してください (ドキュメントを参照)。したがって、この方法で例外を「処理」できますが、例外がコール スタックにスローされるのを防ぐことはできません。

例外を適切に処理して消費したい場合は、try/catchブロックを使用する必要があります。with例外が発生したときに try ブロックがアクティブである限り、ブロックの内側または外側にある可能性があります。

于 2011-08-13T20:11:38.613 に答える
2

oursqlの特定のケースでは、

with some_connection.cursor() as cursor:
    do_something_with(cursor)

と同等です

cursor = some_connection.cursor()
try:
    do_something_with(cursor)
except:
    some_connection.rollback()
    raise
else:
    some_connection.commit()
finally:
    cursor.close()

ご覧のとおり、withステートメントが何をするかは、コンテキスト マネージャー (例: some_connection.cursor()`) によって異なります。

with connection.cursor() as cursor:
    try:
        cursor.execute('some query')
    except IntegrityError as e:
        # handle exception

を処理する正しい方法である場合とそうでない場合がありますIntegrityError-- IntegrityError を外側のスコープで処理したい場合があります。

たとえば、次のようなクエリをログに記録する汎用関数があるとします。

def log_query(query):
    logger.info(query)
    with connection.cursor() as cursor:
        cursor.execute(query)

try:
    log_query(query)
except IntegrityError as err:
     # handler error

IntegrityErrorlog_query 内ではなく、後の段階で sを処理したい場合があります。

于 2011-08-13T20:34:37.820 に答える