1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146
|
function varargout = jsave(filename, varargin)
%
% jsave
% or
% jsave(fname)
% varlist=jsave(fname,'param1',value1,'param2',value2,...)
%
% Store variables in a workspace to a JSON or binary JSON file
%
% authors:Qianqian Fang (q.fang <at> neu.edu)
% created on 2020/05/31
%
% input:
% fname: (optional) output file name; if not given, save to 'default.pmat'
% if fname has a '.json' or '.jdt' suffix, a text-based
% JSON/JData file will be created (slow); if the suffix is '.pmat' or
% '.jdb', a Binary JData (https://github.com/NeuroJSON/bjdata/) file will be created.
% opt: (optional) a struct to store parsing options, opt can be replaced by
% a list of ('param',value) pairs - the param string is equivalent
% to a field in opt. opt can have the following
% fields (first in [.|.] is the default)
%
% ws ['caller'|'base']: the name of the workspace in which the
% variables are to be saved
% vars [{'var1','var2',...}]: cell array of variable names to be saved
% matlab [0|1] if set to 1, use matlab's built-in jsonencode to
% store encoded data to a json file; output file
% must have a suffix of .jdt
%
% all options for savebj/savejson (depends on file suffix)
% can be used to adjust the output unless "'matlab',1" is used
%
% output:
% varlist: a list of variables loaded
%
% examples:
% jsave % save all variables in the 'caller' workspace to jamdata.pmat
% jsave('mydat.pmat','vars', {'v1','v2',...}) % save selected variables
% jsave('mydat.pmat','compression','lzma')
%
% license:
% BSD or GPL version 3, see LICENSE_{BSD,GPLv3}.txt files for details
%
% -- this function is part of JSONLab toolbox (http://openjdata.org/jsonlab)
%
if (nargin == 0)
filename = [pwd filesep 'default.pmat'];
end
opt = varargin2struct(varargin{:});
if (~isfield(opt, 'nthread'))
opt.nthread = 4;
end
if (~isfield(opt, 'compression'))
if (exist('zipmat'))
opt.compression = 'blosc2zstd';
else
opt.compression = 'zlib';
end
end
if (~isfield(opt, 'shuffle'))
opt.shuffle = 1;
end
if (~isfield(opt, 'typesize'))
opt.typesize = 4;
end
ws = jsonopt('ws', 'caller', opt);
allvar = evalin(ws, 'whos');
varlist = jsonopt('vars', {allvar.name}, opt);
[isfound, dontsave] = ismember(varlist, {allvar.name});
if (any(isfound == 0))
error('specified variable is not found');
end
header = struct;
body = struct;
metadata = struct('CreateDate', datestr(now, 29), ...
'CreateTime', datestr(now, 'hh:mm:ss'), ...
'OriginalName', filename, ...
'BJDataVersion', 'v1_draft-2');
vers = ver('MATLAB');
if (isempty(vers))
vers = ver('Octave');
[verstr, releasedate] = version;
vers.Release = verstr;
vers.Date = releasedate;
end
metadata.CreatorApp = vers.Name;
metadata.CreatorVersion = vers.Version;
metadata.CreatorRelease = vers.Release;
metadata.ReleaseDate = vers.Date;
metadata.FormatVersion = 1;
metadata.Parameters = opt;
header.(encodevarname('_DataInfo_')) = metadata;
for i = 1:length(varlist)
header.(varlist{i}) = allvar(dontsave(i));
body.(varlist{i}) = evalin(ws, varlist{i});
end
if (nargout == 1)
varargout{1} = header;
end
defaultopt = {'compression', opt.compression, 'nthread', opt.nthread, ...
'shuffle', opt.shuffle, 'typesize', opt.typesize, 'keeptype', 1, 'array2struct', 1};
if (jsonopt('matlab', 0, opt) && exist('jsonencode', 'builtin'))
if (isempty(regexp(filename, '\.[jJ][sS][oO][nN]$', 'once')))
filename = regexprep(filename, '\.[a-zA-Z]+$', '.jdt');
end
output.WorkspaceHeader = jdataencode(header, 'prefix', 'x', 'base64', 1, varargin{:});
headerjson = jsonencode(output);
clear output;
output.WorkspaceData = jdataencode(body, 'AnnotateArray', 1, 'base64', 1, ...
'UseArrayZipSize', 1, 'MapAsStruct', 1, 'prefix', 'x', defaultopt{:}, varargin{:});
bodyjson = jsonencode(output);
clear output;
fid = fopen(filename, jsonopt('writemode', 'w', opt));
fwrite(fid, headerjson);
fwrite(fid, sprintf('\n\n\n'));
fwrite(fid, bodyjson);
fclose(fid);
elseif (jsonopt('usemmap', 0, opt) == 1)
bodyjson = savejd('WorkspaceData', body, ...
defaultopt{:}, varargin{:});
header.(encodevarname('_MMap_')) = loadjd(bodyjson, 'mmaponly', 1, varargin{:});
savejd('WorkspaceHeader', header, 'filename', filename, varargin{:});
fid = fopen(filename, 'ab+');
fwrite(fid, bodyjson);
fclose(fid);
else
savejd('WorkspaceHeader', header, 'filename', filename, varargin{:});
savejd('WorkspaceData', body, 'filename', filename, 'append', 1, ...
defaultopt{:}, varargin{:});
end
|