Tôi đã tìm ra một cách tương đối đơn giản (nhưng hơi khác thường) để lưu các số liệu matplotlib của mình. Nó hoạt động như thế này:
import libscript
import matplotlib.pyplot as plt
import numpy as np
t = np.arange(0.0, 2.0, 0.01)
s = 1 + np.sin(2*np.pi*t)
#<plot>
plt.plot(t, s)
plt.xlabel('time (s)')
plt.ylabel('voltage (mV)')
plt.title('About as simple as it gets, folks')
plt.grid(True)
plt.show()
#</plot>
save_plot(fileName='plot_01.py',obj=sys.argv[0],sel='plot',ctx=libscript.get_ctx(ctx_global=globals(),ctx_local=locals()))
với chức năng save_plot
được định nghĩa như thế này (phiên bản đơn giản để hiểu logic):
def save_plot(fileName='',obj=None,sel='',ctx={}):
"""
Save of matplolib plot to a stand alone python script containing all the data and configuration instructions to regenerate the interactive matplotlib figure.
Parameters
----------
fileName : [string] Path of the python script file to be created.
obj : [object] Function or python object containing the lines of code to create and configure the plot to be saved.
sel : [string] Name of the tag enclosing the lines of code to create and configure the plot to be saved.
ctx : [dict] Dictionary containing the execution context. Values for variables not defined in the lines of code for the plot will be fetched from the context.
Returns
-------
Return ``'done'`` once the plot has been saved to a python script file. This file contains all the input data and configuration to re-create the original interactive matplotlib figure.
"""
import os
import libscript
N_indent=4
src=libscript.get_src(obj=obj,sel=sel)
src=libscript.prepend_ctx(src=src,ctx=ctx,debug=False)
src='\n'.join([' '*N_indent+line for line in src.split('\n')])
if(os.path.isfile(fileName)): os.remove(fileName)
with open(fileName,'w') as f:
f.write('import sys\n')
f.write('sys.dont_write_bytecode=True\n')
f.write('def main():\n')
f.write(src+'\n')
f.write('if(__name__=="__main__"):\n')
f.write(' '*N_indent+'main()\n')
return 'done'
hoặc xác định chức năng save_plot
như thế này (phiên bản tốt hơn sử dụng nén zip để tạo ra các tệp hình nhẹ hơn):
def save_plot(fileName='',obj=None,sel='',ctx={}):
import os
import json
import zlib
import base64
import libscript
N_indent=4
level=9#0 to 9, default: 6
src=libscript.get_src(obj=obj,sel=sel)
obj=libscript.load_obj(src=src,ctx=ctx,debug=False)
bin=base64.b64encode(zlib.compress(json.dumps(obj),level))
if(os.path.isfile(fileName)): os.remove(fileName)
with open(fileName,'w') as f:
f.write('import sys\n')
f.write('sys.dont_write_bytecode=True\n')
f.write('def main():\n')
f.write(' '*N_indent+'import base64\n')
f.write(' '*N_indent+'import zlib\n')
f.write(' '*N_indent+'import json\n')
f.write(' '*N_indent+'import libscript\n')
f.write(' '*N_indent+'bin="'+str(bin)+'"\n')
f.write(' '*N_indent+'obj=json.loads(zlib.decompress(base64.b64decode(bin)))\n')
f.write(' '*N_indent+'libscript.exec_obj(obj=obj,tempfile=False)\n')
f.write('if(__name__=="__main__"):\n')
f.write(' '*N_indent+'main()\n')
return 'done'
Điều này làm cho việc sử dụng một mô-đun libscript
của riêng tôi, chủ yếu dựa vào các mô-đun inspect
và ast
. Tôi có thể cố gắng chia sẻ nó trên Github nếu sự quan tâm được bày tỏ (trước tiên nó sẽ yêu cầu một số dọn dẹp và tôi bắt đầu với Github).
Ý tưởng đằng sau save_plot
chức năng và libscript
mô-đun này là tìm nạp các hướng dẫn python tạo hình (sử dụng mô-đun inspect
), phân tích chúng (sử dụng mô-đun ast
) để trích xuất tất cả các biến, chức năng và mô-đun nhập nó dựa vào, trích xuất chúng từ ngữ cảnh thực thi và tuần tự hóa chúng như hướng dẫn python (mã cho các biến sẽ giống như t=[0.0,2.0,0.01]
... và mã cho các mô-đun sẽ giống nhưimport matplotlib.pyplot as plt
...) được thêm vào trước các hướng dẫn hình. Các hướng dẫn python kết quả được lưu dưới dạng tập lệnh python mà việc thực thi sẽ xây dựng lại hình matplotlib ban đầu.
Như bạn có thể tưởng tượng, điều này hoạt động tốt cho hầu hết (nếu không phải tất cả) số liệu matplotlib.