|
| 1 | +## Poly{T} is basically T[x], with T a Ring. |
| 2 | +## T[x] may not have an order so abs, comparing to 0 may not be defined. |
1 | 3 |
|
2 |
| -function show(io::IO, p::Poly) |
3 |
| - print(io,"Poly(") |
4 |
| - print(io,p) |
5 |
| - print(io,")") |
| 4 | +## to handle this case we create some functions |
| 5 | +## which can be modified by users for other Ts |
| 6 | + |
| 7 | +"`hasneg(::T)` attribute is true if: `pj < zero(T)` is defined." |
| 8 | +hasneg{T}(::Type{T}) = false |
| 9 | + |
| 10 | +"Could value possibly be negative and if so, is it?" |
| 11 | +isneg{T}(pj::T) = hasneg(T) && pj < zero(T) |
| 12 | + |
| 13 | +"Make `pj` positive if it is negative. (Don't call `abs` as that may not be defined, or appropriate.)" |
| 14 | +aspos{T}(pj::T) = (hasneg(T) && isneg(pj)) ? -pj : pj |
| 15 | + |
| 16 | +"Should a value of `one(T)` be shown as a coefficient of monomial `x^i`, `i >= 1`? (`1.0x^2` is shown, `1 x^2` is not)" |
| 17 | +showone{T}(::Type{T}) = true |
| 18 | + |
| 19 | + |
| 20 | +##### |
| 21 | + |
| 22 | +## Numbers |
| 23 | +hasneg{T<:Real}(::Type{T}) = true |
| 24 | + |
| 25 | +### Integer |
| 26 | +showone{T<:Integer}(::Type{T}) = false |
| 27 | +showone{T}(::Type{Rational{T}}) = false |
| 28 | + |
| 29 | + |
| 30 | + |
| 31 | + |
| 32 | +### Complex coefficients |
| 33 | +hasneg{T}(::Type{Complex{T}}) = true ## we say neg if real(z) < 0 || real(z) == 0 and imag(g) < 0 |
| 34 | + |
| 35 | +function isneg{T}(pj::Complex{T}) |
| 36 | + real(pj) < 0 && return true |
| 37 | + (real(pj) == 0 && imag(pj) < 0) && return(true) |
| 38 | + return false |
6 | 39 | end
|
7 | 40 |
|
8 |
| -function printexponent(io,var,i) |
9 |
| - if i == 0 |
10 |
| - elseif i == 1 |
11 |
| - print(io,var) |
12 |
| - else |
13 |
| - print(io,var,"^",i) |
| 41 | +showone{T}(pj::Type{Complex{T}}) = showone(T) |
| 42 | + |
| 43 | + |
| 44 | +### Polynomials as coefficients |
| 45 | +hasneg{S}(::Type{Poly{S}}) = false |
| 46 | +showone{S}(::Type{Poly{S}}) = false |
| 47 | + |
| 48 | + |
| 49 | +##### |
| 50 | + |
| 51 | +"Show different operations depending on mimetype. `l-` is leading minus sign." |
| 52 | +function showop(::MIME"text/plain", op) |
| 53 | + d = Dict("*" => "⋅", "+" => " + ", "-" => " - ", "l-" => "-") |
| 54 | + d[op] |
| 55 | +end |
| 56 | + |
| 57 | +function showop(::MIME"text/latex", op) |
| 58 | + d = Dict("*" => "\\cdot ", "+" => " + ", "-" => " - ", "l-" => "-") |
| 59 | + d[op] |
| 60 | +end |
| 61 | + |
| 62 | +function showop(::MIME"text/html", op) |
| 63 | + d = Dict("*" => "∙", "+" => " + ", "-" => " - ", "l-" => "-") |
| 64 | + d[op] |
| 65 | +end |
| 66 | + |
| 67 | + |
| 68 | + |
| 69 | +### |
| 70 | + |
| 71 | +function printpoly{T}(io::IO, p::Poly{T}, mimetype) |
| 72 | + first = true |
| 73 | + printed_anything = false |
| 74 | + for i in eachindex(p) |
| 75 | + printed = showterm(io,p,i,first, mimetype) |
| 76 | + first &= !printed |
| 77 | + printed_anything |= printed |
14 | 78 | end
|
| 79 | + printed_anything || print(io, zero(T)) |
15 | 80 | end
|
16 | 81 |
|
17 |
| -function printterm{T}(io::IO,p::Poly{T},j,first) |
| 82 | +function showterm{T}(io::IO,p::Poly{T},j,first, mimetype) |
18 | 83 | pj = p[j]
|
19 |
| - if pj == zero(T) |
20 |
| - return false |
21 |
| - end |
22 |
| - neg = pj < zero(T) |
23 |
| - if first |
24 |
| - neg && print(io, "-") #Prepend - if first and negative |
25 |
| - else |
26 |
| - neg ? print(io, " - ") : print(io," + ") |
27 |
| - end |
28 |
| - pj = abs(pj) |
29 |
| - if pj != one(T) || j == 0 |
30 |
| - show(io,pj) |
31 |
| - end |
32 |
| - printexponent(io,p.var,j) |
| 84 | + |
| 85 | + pj == zero(T) && return false |
| 86 | + |
| 87 | + pj = printsign(io, pj, j, first, mimetype) |
| 88 | + printcoefficient(io, pj, j, mimetype) |
| 89 | + printproductsign(io, pj, j, mimetype) |
| 90 | + printexponent(io,p.var,j, mimetype) |
33 | 91 | true
|
34 | 92 | end
|
35 | 93 |
|
36 |
| -function printterm{T<:Complex}(io::IO,p::Poly{T},j,first) |
37 |
| - pj = p[j] |
38 |
| - abs_repj = abs(real(pj)) |
39 |
| - abs_impj = abs(imag(pj)) |
40 |
| - if abs_repj < 2*eps(T) && abs_impj < 2*eps(T) |
41 |
| - return false |
42 |
| - end |
43 | 94 |
|
44 |
| - # We show a negative sign either for any complex number with negative |
45 |
| - # real part (and then negate the immaginary part) of for complex |
46 |
| - # numbers that are pure imaginary with negative imaginary part |
47 |
| - |
48 |
| - neg = ((abs_repj > 2*eps(T)) && real(pj) < 0) || |
49 |
| - ((abs_impj > 2*eps(T)) && imag(pj) < 0) |
50 | 95 |
|
| 96 | +## print the sign |
| 97 | +## returns aspos(pj) |
| 98 | +function printsign{T}(io::IO, pj::T, j, first, mimetype) |
| 99 | + neg = isneg(pj) |
51 | 100 | if first
|
52 |
| - neg && print(io, "-") #Prepend - if first and negative |
| 101 | + neg && print(io, showop(mimetype, "l-")) #Prepend - if first and negative |
53 | 102 | else
|
54 |
| - neg ? print(io," - ") : print(io," + ") |
| 103 | + neg ? print(io, showop(mimetype, "-")) : print(io,showop(mimetype, "+")) |
55 | 104 | end
|
| 105 | + |
| 106 | + aspos(pj) |
| 107 | +end |
| 108 | + |
| 109 | +## print * or cdot, ... |
| 110 | +function printproductsign{T}(io::IO, pj::T, j, mimetype) |
| 111 | + j == 0 && return |
| 112 | + (showone(T) || pj != one(T)) && print(io, showop(mimetype, "*")) |
| 113 | +end |
| 114 | + |
| 115 | +function printcoefficient{T}(io::IO, pj::Complex{T}, j, mimetype) |
| 116 | + |
| 117 | + hasreal = abs(real(pj)) > 0 |
| 118 | + hasimag = abs(imag(pj)) > 0 |
56 | 119 |
|
57 |
| - if abs_repj > 2*eps(T) #Real part is not 0 |
58 |
| - if abs_impj > 2*eps(T) #Imag part is not 0 |
59 |
| - print(io,'(',neg ? -pj : pj,')') |
60 |
| - else |
61 |
| - print(io, neg ? -real(pj) : real(pj)) |
62 |
| - end |
| 120 | + if hasreal & hasimag |
| 121 | + print(io, '(') |
| 122 | + show(io, mimetype, pj) |
| 123 | + print(io, ')') |
| 124 | + elseif hasreal |
| 125 | + a = real(pj) |
| 126 | + (showone(T) || a != one(T)) && show(io, mimetype, a) |
| 127 | + elseif hasimag |
| 128 | + b = imag(pj) |
| 129 | + (showone(T) || b != one(T)) && show(io, mimetype, b) |
| 130 | + show(io, mimetype, im) |
63 | 131 | else
|
64 |
| - if abs_impj > 2*eps(T) |
65 |
| - print(io,'(', abs(imag(pj)),"im)") |
66 |
| - end |
| 132 | + return |
67 | 133 | end
|
68 |
| - printexponent(io,p.var,j) |
69 |
| - true |
70 | 134 | end
|
71 | 135 |
|
72 |
| -function print{T}(io::IO, p::Poly{T}) |
73 |
| - first = true |
74 |
| - printed_anything = false |
75 |
| - n = length(p)-1 |
76 |
| - for i = 0:n |
77 |
| - printed = printterm(io,p,i,first) |
78 |
| - first &= !printed |
79 |
| - printed_anything |= printed |
| 136 | + |
| 137 | +## show a single term |
| 138 | +function printcoefficient{T}(io::IO, pj::T, j, mimetype) |
| 139 | + pj == one(T) && !(showone(T) || j == 0) && return |
| 140 | + show(io, mimetype, pj) |
| 141 | +end |
| 142 | + |
| 143 | +## show exponent |
| 144 | +function printexponent(io,var,i, mimetype::MIME"text/latex") |
| 145 | + if i == 0 |
| 146 | + return |
| 147 | + elseif i == 1 |
| 148 | + print(io,var) |
| 149 | + else |
| 150 | + print(io,var,"^{$i}") |
| 151 | + end |
| 152 | +end |
| 153 | + |
| 154 | +function printexponent(io,var,i, mimetype) |
| 155 | + if i == 0 |
| 156 | + return |
| 157 | + elseif i == 1 |
| 158 | + print(io,var) |
| 159 | + else |
| 160 | + print(io,var,"^",i) |
80 | 161 | end
|
81 |
| - printed_anything || print(io,zero(T)) |
| 162 | +end |
| 163 | + |
| 164 | + |
| 165 | +#### |
| 166 | + |
| 167 | +## text/plain |
| 168 | +@compat Base.show{T}(io::IO, p::Poly{T}) = show(io, MIME("text/plain"), p) |
| 169 | +@compat function Base.show{T}(io::IO, mimetype::MIME"text/plain", p::Poly{T}) |
| 170 | + print(io,"Poly(") |
| 171 | + printpoly(io, p, mimetype) |
| 172 | + print(io,")") |
| 173 | + |
| 174 | +end |
| 175 | + |
| 176 | +## text/latex |
| 177 | +@compat function Base.show{T}(io::IO, mimetype::MIME"text/latex", p::Poly{T}) |
| 178 | + print(io, "\$") |
| 179 | + printpoly(io, p, mimetype) |
| 180 | + print(io, "\$") |
| 181 | +end |
| 182 | + |
| 183 | +@compat function Base.show{T}(io::IO, mimetype::MIME"text/latex", a::Rational{T}) |
| 184 | + abs(a.den) == one(T) ? print(io, a.num) : print(io, "\\frac{$(a.num)}{$(a.den)}") |
| 185 | +end |
| 186 | + |
| 187 | +@compat function Base.show{T<:Number}(io::IO, mimetype::MIME"text/latex", a::T) |
| 188 | + print(io, a) |
| 189 | +end |
| 190 | + |
| 191 | + |
| 192 | +## text/html |
| 193 | +@compat function Base.show{T}(io::IO, mimetype::MIME"text/html", p::Poly{T}) |
| 194 | + printpoly(io, p, mimetype) |
| 195 | +end |
| 196 | + |
| 197 | +@compat function Base.show{T<:Number}(io::IO, mimetype::MIME"text/html", a::T) |
| 198 | + print(io, a) |
82 | 199 | end
|
0 commit comments