1%% Copyright (C) 2014-2016, 2019 Colin B. Macdonald 2%% 3%% This file is part of OctSymPy. 4%% 5%% OctSymPy is free software; you can redistribute it and/or modify 6%% it under the terms of the GNU General Public License as published 7%% by the Free Software Foundation; either version 3 of the License, 8%% or (at your option) any later version. 9%% 10%% This software is distributed in the hope that it will be useful, 11%% but WITHOUT ANY WARRANTY; without even the implied warranty 12%% of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See 13%% the GNU General Public License for more details. 14%% 15%% You should have received a copy of the GNU General Public 16%% License along with this software; see the file COPYING. 17%% If not, see <http://www.gnu.org/licenses/>. 18 19%% -*- texinfo -*- 20%% @documentencoding UTF-8 21%% @defmethod @@sym display (@var{x}) 22%% Display, on command line, the contents of a symbolic expression. 23%% 24%% Examples: 25%% @example 26%% @group 27%% x = sym('x') 28%% @result{} x = (sym) x 29%% 30%% display(x) 31%% @result{} x = (sym) x 32%% 33%% display([x 2 pi]) 34%% @result{} (sym) [x 2 π] (1×3 matrix) 35%% @end group 36%% @end example 37%% 38%% Other examples: 39%% @example 40%% @group 41%% A = sym([1 2; 3 4]) 42%% @result{} A = (sym 2×2 matrix) 43%% ⎡1 2⎤ 44%% ⎢ ⎥ 45%% ⎣3 4⎦ 46%% @end group 47%% 48%% @group 49%% syms n 50%% A = sym('A', [n n]) 51%% @result{} A = (sym) A (n×n matrix expression) 52%% B = 3*A 53%% @result{} B = (sym) 3⋅A (n×n matrix expression) 54%% 55%% A = sym(ones(0, 3)) 56%% @result{} A = (sym) [] (empty 0×3 matrix) 57%% 58%% A = sym('A', [0, n]) 59%% @result{} A = (sym) A (empty 0×n matrix expression) 60%% B = 3*A 61%% @result{} B = (sym) 3⋅A (empty 0×n matrix expression) 62%% @end group 63%% @end example 64%% 65%% @seealso{@@sym/disp} 66%% @end defmethod 67 68 69function display(x) 70 71 %% Settings 72 wh = sympref('display'); 73 if (strcmp(wh, 'unicode')) 74 unicode_dec = true; 75 else 76 unicode_dec = false; 77 end 78 if (exist('OCTAVE_VERSION', 'builtin') && ... 79 compare_versions (OCTAVE_VERSION (), '4.3.0', '>=')) 80 [fmt, spacing] = format(); 81 loose = strcmp (spacing, 'loose'); 82 elseif (exist('OCTAVE_VERSION', 'builtin') && ... 83 compare_versions (OCTAVE_VERSION (), '4.0.0', '>=')) 84 % Octave 4.1 dropped (temporarily?) the get(0,...) approach 85 loose = eval('! __compactformat__ ()'); 86 else 87 % Matlab and Octave < 4 88 loose = strcmp(get(0, 'FormatSpacing'), 'loose'); 89 end 90 91 % weird hack to support "ans(x) = " output for @symfun 92 name = private_disp_name(x, inputname (1)); 93 94 dispstr = disp (x); 95 dispstrtrim = strtrim (dispstr); 96 hasnewlines = ~isempty (strfind (dispstrtrim, sprintf('\n'))); 97 98 [desc_start, desc_end] = sym_describe (x, unicode_dec); 99 100 toobig = hasnewlines; 101 %toobig = hasnewlines || ~(isempty(x) || isscalar(x)); 102 103 s1 = ''; 104 if (~isempty(name)) 105 s1 = sprintf ('%s = ', name); 106 end 107 108 if (toobig) 109 if (isempty(desc_end)) 110 s2 = sprintf('(%s)', desc_start); 111 else 112 s2 = sprintf('(%s %s)', desc_start, desc_end); 113 end 114 else 115 if (isempty(desc_end)) 116 s2 = sprintf('(%s) %s', desc_start, dispstrtrim); 117 else 118 s2 = sprintf('(%s) %s (%s)', desc_start, dispstrtrim, desc_end); 119 end 120 end 121 s = [s1 s2]; 122 disp (s) 123 124 if (toobig) 125 if (loose), fprintf ('\n'); end 126 % don't use printf b/c ascii-art might have slashes 127 disp (dispstr(1:end-1)); % remove existing newline, disp adds one 128 if (loose), fprintf ('\n'); end 129 end 130end 131 132 133function [s1 s2] = sym_describe(x, unicode_dec) 134 if (unicode_dec) 135 %timesstr = '×'; % https://savannah.gnu.org/bugs/index.php?56072 136 timesstr = do_highbyte_escapes('\xc3\x97'); 137 else 138 timesstr = 'x'; 139 end 140 141 s1 = class (x); 142 srepr = sympy (x); 143 d = size (x); 144 145 % sort of isinstance(x, MatrixExpr) but cheaper 146 is_matrix_symbol = false; 147 matexprlist = {'MatrixSymbol' 'MatMul' 'MatAdd' 'MatPow'}; 148 for i=1:length(matexprlist) 149 if (strncmp(srepr, matexprlist{i}, length(matexprlist{i}))) 150 is_matrix_symbol = true; 151 end 152 end 153 154 if (isscalar (x)) && (~is_matrix_symbol) 155 s2 = ''; 156 elseif (is_matrix_symbol) 157 %if (any(isnan(d))) % may not tell the truth 158 if (any(isnan(x.size))) 159 [nn, mm] = pycall_sympy__ ('return (_ins[0].rows, _ins[0].cols)', x); 160 numrstr = strtrim(disp(nn, 'flat')); 161 numcstr = strtrim(disp(mm, 'flat')); 162 else 163 nn = d(1); mm = d(2); 164 numrstr = num2str(d(1), '%g'); 165 numcstr = num2str(d(2), '%g'); 166 end 167 if (logical(nn == 0) || logical(mm == 0)) 168 estr = 'empty '; 169 else 170 estr = ''; 171 end 172 s2 = sprintf ('%s%s%s%s matrix expression', estr, numrstr, timesstr, numcstr); 173 elseif (length (d) == 2) 174 if (isempty (x)) 175 estr = 'empty '; 176 else 177 estr = ''; 178 end 179 s2 = sprintf ('%s%g%s%g matrix', estr, d(1), timesstr, d(2)); 180 else 181 s2 = sprintf ('%d-dim array', length (d)) 182 end 183end 184 185 186% FIXME: Could quietly test with "evalc", but [missing in 187% Octave](https://savannah.gnu.org/patch/?8033). For now, a dummy 188% test. Doctests will cover this anyway. 189%!test 190%! assert(true) 191