Skip to content

Commit 0d1f490

Browse files
committed
Fix arb.repr() and have it round trip
1 parent 5e387c9 commit 0d1f490

File tree

4 files changed

+52
-16
lines changed

4 files changed

+52
-16
lines changed

src/flint/test/test_all.py

Lines changed: 27 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1647,14 +1647,32 @@ def test_nmod_series():
16471647

16481648

16491649
def test_arb():
1650-
A = flint.arb
1651-
assert A(3) > A(2.5)
1652-
assert A(3) >= A("2.5")
1653-
assert A(3) < A((3,1))
1654-
assert A(3) <= A("inf")
1655-
assert A(3) == A(3)
1656-
assert A(3) != A(2)
1657-
assert not (A("1.1") == A("1.1"))
1650+
arb = flint.arb
1651+
assert arb(3) > arb(2.5)
1652+
assert arb(3) >= arb("2.5")
1653+
assert arb(3) < arb((3,1))
1654+
assert arb(3) <= arb("inf")
1655+
assert arb(3) == arb(3)
1656+
assert arb(3) != arb(2)
1657+
assert not (arb("1.1") == arb("1.1"))
1658+
1659+
assert arb(3).repr() == 'arb((0x3, 0x0))'
1660+
assert arb("nan").repr() == "arb('nan')"
1661+
assert arb(0, "inf").repr() == "arb(0.0, '+inf')"
1662+
assert arb((1,2), (3,4)).repr() == "arb((0x1, 0x2), (0x3, 0x4))"
1663+
assert arb(1, arb("inf")).repr() == "arb((0x1, 0x0), '+inf')"
1664+
assert arb(1, "inf").repr() == "arb((0x1, 0x0), '+inf')"
1665+
assert arb(1, "nan").repr() == "arb((0x1, 0x0), '+inf')"
1666+
assert arb("nan", 1).repr() == "arb('nan')"
1667+
assert arb("nan", "nan").repr() == "arb('nan')"
1668+
1669+
for a in [arb(2), arb((1,2), (3,4)), arb("nan"), arb(0, "inf")]:
1670+
assert eval(a.repr()).repr() == a.repr()
1671+
1672+
1673+
def test_acb():
1674+
acb = flint.acb
1675+
assert acb(1, 2).repr() == "acb(arb((0x1, 0x0)), arb((0x1, 0x1)))"
16581676

16591677

16601678
def test_pickling():
@@ -5038,6 +5056,7 @@ def test_all_tests():
50385056
test_fq_default_poly,
50395057

50405058
test_arb,
5059+
test_acb,
50415060

50425061
test_pickling,
50435062

src/flint/types/arb.pxd

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,3 +15,5 @@ cdef class arb(flint_scalar):
1515
cpdef bint is_nan(self)
1616
cpdef bint is_exact(self)
1717
cpdef bint is_integer(self)
18+
19+
cdef tuple _to_arfs(self)

src/flint/types/arb.pyx

Lines changed: 21 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -196,14 +196,21 @@ cdef class arb(flint_scalar):
196196
arb_clear(self.val)
197197

198198
def __init__(self, mid=None, rad=None):
199+
cdef arf _rad
200+
cdef fmpz man, exp
199201
if mid is not None:
200202
if arb_set_python(self.val, mid, 1) == 0:
201203
raise TypeError("cannot create arb from type %s" % type(mid))
202204
if rad is not None:
203-
rad = arb(rad)
204-
arb_add_error(self.val, (<arb>rad).val)
205-
# rad = arf(rad)
206-
# arb_add_error_arf(self.val, (<arf>rad).val)
205+
if isinstance(rad, tuple):
206+
# Set the radius exactly from tuple of ints so that
207+
# eval(a.repr()) round trips.
208+
_rad = arf(rad)
209+
man, exp = _rad.man_exp()
210+
mag_set_fmpz_2exp_fmpz(arb_radref(self.val), man.val, exp.val)
211+
else:
212+
rad = arb(rad)
213+
arb_add_error(self.val, (<arb>rad).val)
207214

208215
cpdef bint is_zero(self):
209216
return arb_is_zero(self.val)
@@ -385,10 +392,17 @@ cdef class arb(flint_scalar):
385392
else:
386393
return (0, man, int(exp), man.bit_length())
387394

395+
# Make this a public function?
396+
cdef tuple _to_arfs(self):
397+
cdef arf mid = arf.__new__(arf)
398+
cdef arf rad = arf.__new__(arf)
399+
arf_set(mid.val, arb_midref(self.val))
400+
arf_set_mag(rad.val, arb_radref(self.val))
401+
return (mid, rad)
402+
388403
def repr(self):
389-
mid = self.mid()
390-
rad = self.rad()
391-
if rad.is_zero():
404+
mid, rad = self._to_arfs()
405+
if rad.is_zero() or mid.is_nan():
392406
return "arb(%s)" % mid._repr_str()
393407
else:
394408
return "arb(%s, %s)" % (mid._repr_str(), rad._repr_str())

src/flint/types/arf.pyx

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,8 @@ cdef class arf:
9494
if arf_is_zero(self.val):
9595
return "0.0"
9696
elif arf_is_finite(self.val):
97-
return "(%s, %s)" % self.man_exp()
97+
man, exp = self.man_exp()
98+
return "(%s, %s)" % (hex(man), hex(exp))
9899
elif arf_is_pos_inf(self.val):
99100
return "'+inf'"
100101
elif arf_is_neg_inf(self.val):

0 commit comments

Comments
 (0)