This issue tracker has been migrated to GitHub ,
and is currently read-only.
For more information,
see the GitHub FAQs in the Python's Developer Guide.
Created on 2008年08月07日 10:54 by ocean-city, last changed 2022年04月11日 14:56 by admin. This issue is now closed.
| Messages (7) | |||
|---|---|---|---|
| msg70816 - (view) | Author: Hirokazu Yamamoto (ocean-city) * (Python committer) | Date: 2008年08月07日 10:54 | |
I'm not sure this is bug or not, but shouldn't `io' be collected by
refcount GC? This happens on python2.5 but doesn't happend on python3.0.
import os
def foo():
io = open("a.txt", "w")
raise RuntimeError()
try:
foo()
except:
pass
os.remove("a.txt") # WindowsError (Error32)
# Process cannot access to the file.
# Another process is using it.
|
|||
| msg70817 - (view) | Author: Martin v. Löwis (loewis) * (Python committer) | Date: 2008年08月07日 11:32 | |
The interpreter holds onto sys.exc_traceback even after the except block. This refers to the frame, which refers to the file object. |
|||
| msg70819 - (view) | Author: Hirokazu Yamamoto (ocean-city) * (Python committer) | Date: 2008年08月07日 12:55 | |
Hmm, when exception occurs in some frame, its reference will be
retained even after exiting function? Indeed, extra
exception fixed problem.
import os
def foo():
io = open("a.txt", "w")
raise RuntimeError()
try:
foo()
except:
pass
try:
raise RuntimeError()
except:
pass
os.remove("a.txt") # fine
But still I'm little confused why this code prints "del".
class A:
def __del__(self):
print "del"
def foo():
a = A()
raise RuntimeError()
try:
foo()
except:
pass
I found this behavior when investigating issue3210. When
Lib/subprocess.py (814)'s CreateProcess() raises exception,
p2cread will be freed by refcount GC, it never happen before
os.remove(). And this error is also fixed by same hack.
import subprocess, os
file = open("filename", "w")
try:
proc = subprocess.Popen("nosuchprogram", stdout=file)
except OSError:
pass
try:
raise RuntimeError() # hack
except:
pass
file.close()
os.remove("filename")
|
|||
| msg70820 - (view) | Author: Hirokazu Yamamoto (ocean-city) * (Python committer) | Date: 2008年08月07日 12:58 | |
>But still I'm little confused why this code prints "del". Oh, sorry, kick me. "del" should be printed when interpreter exits. :-) |
|||
| msg70821 - (view) | Author: Martin v. Löwis (loewis) * (Python committer) | Date: 2008年08月07日 13:05 | |
> Hmm, when exception occurs in some frame, its reference will be > retained even after exiting function? Correct. When a traceback is produced, all frames get linked, be able to print later the traceback with source code information. Each frame keeps all its local variables. |
|||
| msg70823 - (view) | Author: Hirokazu Yamamoto (ocean-city) * (Python committer) | Date: 2008年08月07日 13:37 | |
I understand. Thank you. |
|||
| msg70825 - (view) | Author: Antoine Pitrou (pitrou) * (Python committer) | Date: 2008年08月07日 13:43 | |
You don't need to raise another exception, calling sys.exc_clear()
should be fine. But a cleaner way to write your example is:
def foo():
with open("a.txt", "w") as io:
raise RuntimeError()
"with" will automatically close the file when the block exits.
If you are concerned with Python < 2.5 compatibility, use "try: ...
finally:" instead.
And, you're right, the problem doesn't occur at all in Python 3.0
because the exception is cleaned up after the end of the "except:" block
catching it.
|
|||
| History | |||
|---|---|---|---|
| Date | User | Action | Args |
| 2022年04月11日 14:56:37 | admin | set | github: 47765 |
| 2008年08月07日 13:43:13 | pitrou | set | status: open -> closed nosy: + pitrou resolution: not a bug messages: + msg70825 |
| 2008年08月07日 13:37:40 | ocean-city | set | messages: + msg70823 |
| 2008年08月07日 13:05:07 | loewis | set | messages: + msg70821 |
| 2008年08月07日 12:58:03 | ocean-city | set | messages: + msg70820 |
| 2008年08月07日 12:55:41 | ocean-city | set | messages: + msg70819 |
| 2008年08月07日 11:32:18 | loewis | set | nosy:
+ loewis messages: + msg70817 |
| 2008年08月07日 10:54:51 | ocean-city | create | |