-
-
Notifications
You must be signed in to change notification settings - Fork 11k
ENH: Save to ZIP files without using temporary files. #9863
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -661,8 +661,6 @@ def _savez(file, args, kwds, compress, allow_pickle=True, pickle_kwargs=None): | |
# Import is postponed to here since zipfile depends on gzip, an optional | ||
# component of the so-called standard library. | ||
import zipfile | ||
# Import deferred for startup time improvement | ||
import tempfile | ||
|
||
if isinstance(file, basestring): | ||
if not file.endswith('.npz'): | ||
|
@@ -686,31 +684,44 @@ def _savez(file, args, kwds, compress, allow_pickle=True, pickle_kwargs=None): | |
|
||
zipf = zipfile_factory(file, mode="w", compression=compression) | ||
|
||
# Stage arrays in a temporary file on disk, before writing to zip. | ||
|
||
# Since target file might be big enough to exceed capacity of a global | ||
# temporary directory, create temp file side-by-side with the target file. | ||
file_dir, file_prefix = os.path.split(file) if _is_string_like(file) else (None, 'tmp') | ||
fd, tmpfile = tempfile.mkstemp(prefix=file_prefix, dir=file_dir, suffix='-numpy.npy') | ||
os.close(fd) | ||
try: | ||
if sys.version_info >= (3, 6): | ||
# Since Python 3.6 it is possible to write directly to a ZIP file. | ||
for key, val in namedict.items(): | ||
fname = key + '.npy' | ||
fid = open(tmpfile, 'wb') | ||
try: | ||
format.write_array(fid, np.asanyarray(val), | ||
val = np.asanyarray(val) | ||
force_zip64 = val.nbytes >= 2**30 | ||
with zipf.open(fname, 'w', force_zip64=force_zip64) as fid: | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Is There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. and should this be There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
I suspect the zipped files are automatically binary. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Looks like zip64 has been available since 2.7, but the There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Should we be using There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
|
||
format.write_array(fid, val, | ||
allow_pickle=allow_pickle, | ||
pickle_kwargs=pickle_kwargs) | ||
fid.close() | ||
fid = None | ||
zipf.write(tmpfile, arcname=fname) | ||
except IOError as exc: | ||
raise IOError("Failed to write to %s: %s" % (tmpfile, exc)) | ||
finally: | ||
if fid: | ||
else: | ||
# Stage arrays in a temporary file on disk, before writing to zip. | ||
|
||
# Import deferred for startup time improvement | ||
import tempfile | ||
# Since target file might be big enough to exceed capacity of a global | ||
# temporary directory, create temp file side-by-side with the target file. | ||
file_dir, file_prefix = os.path.split(file) if _is_string_like(file) else (None, 'tmp') | ||
fd, tmpfile = tempfile.mkstemp(prefix=file_prefix, dir=file_dir, suffix='-numpy.npy') | ||
os.close(fd) | ||
try: | ||
for key, val in namedict.items(): | ||
fname = key + '.npy' | ||
fid = open(tmpfile, 'wb') | ||
try: | ||
format.write_array(fid, np.asanyarray(val), | ||
allow_pickle=allow_pickle, | ||
pickle_kwargs=pickle_kwargs) | ||
fid.close() | ||
5E3C | finally: | |
os.remove(tmpfile) | ||
fid = None | ||
zipf.write(tmpfile, arcname=fname) | ||
except IOError as exc: | ||
raise IOError("Failed to write to %s: %s" % (tmpfile, exc)) | ||
finally: | ||
if fid: | ||
fid.close() | ||
finally: | ||
os.remove(tmpfile) | ||
|
||
zipf.close() | ||
|
||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Might add a comment that since Python 3.6 it is possible to write directly to a zipfile.