115115 3.146264369941973?
116116 sage: QQbar(I)
117117 I
118- sage: AA(I)
119- Traceback (most recent call last):
120- ...
121- ValueError: Cannot coerce algebraic number with non-zero imaginary part to algebraic real
122118 sage: QQbar(I * golden_ratio)
123119 1.618033988749895?*I
124120 sage: AA(golden_ratio)^2 - AA(golden_ratio)
150146 sage: QQbar(-1)^(1/3)
151147 0.500000000000000? + 0.866025403784439?*I
152148
153- We can explicitly coerce from `\QQ[I]`. (Technically, this is not quite
154- kosher, since `\QQ[I]` does not come with an embedding; we do not know
155- whether the field generator is supposed to map to `+I` or `-I`. We assume
156- that for any quadratic field with polynomial `x^2+1`, the generator maps
157- to `+I`.)::
158-
159- sage: K.<im> = QQ[I]
160- sage: pythag = QQbar(3/5 + 4*im/5); pythag
161- 4/5*I + 3/5
162- sage: pythag.abs() == 1
163- True
149+ However, implicit coercion from `\QQ[I]` is only allowed when it is equipped
150+ with a complex embedding::
164151
165- However, implicit coercion from `\QQ[I]` is not allowed::
152+ sage: i.parent()
153+ Number Field in I with defining polynomial x^2 + 1 with I = 1*I
154+ sage: QQbar(1) + i
155+ I + 1
166156
157+ sage: K.<im> = QuadraticField(-1, embedding=None)
167158 sage: QQbar(1) + im
168159 Traceback (most recent call last):
169160 ...
170- TypeError: unsupported operand parent(s) for +: 'Algebraic Field' and 'Number Field in I with defining polynomial x^2 + 1 with I = 1*I'
161+ TypeError: unsupported operand parent(s) for +: 'Algebraic Field' and
162+ 'Number Field in im with defining polynomial x^2 + 1'
163+
164+ However, we can explicitly coerce from the abstract number field `\QQ[I]`.
165+ (Technically, this is not quite kosher, since we do not know whether the field
166+ generator is supposed to map to `+I` or `-I`. We assume that for any quadratic
167+ field with polynomial `x^2+1`, the generator maps to `+I`.)::
168+
169+ sage: pythag = QQbar(3/5 + 4*im/5); pythag
170+ 4/5*I + 3/5
171+ sage: pythag.abs() == 1
172+ True
171173
172174We can implicitly coerce from algebraic reals to algebraic numbers::
173175
553555import operator
554556
555557import sage .rings .ring
558+ import sage .rings .number_field .number_field_base
556559from sage .misc .fast_methods import Singleton
557560from sage .misc .cachefunc import cached_method
561+ from sage .structure .coerce import parent_is_numerical , parent_is_real_numerical
558562from sage .structure .sage_object import SageObject
559563from sage .structure .richcmp import (richcmp , richcmp_method ,
560564 rich_to_bool , richcmp_not_equal ,
569573from sage .rings .integer_ring import ZZ
570574from sage .rings .rational_field import QQ
571575from sage .rings .number_field .number_field import NumberField , GaussianField , CyclotomicField
572- from sage .rings .number_field .number_field_element_quadratic import NumberFieldElement_quadratic
576+ from sage .rings .number_field .number_field_element_quadratic import NumberFieldElement_quadratic , NumberFieldElement_gaussian
573577from sage .arith .all import factor
574578from . import infinity
575579from sage .categories .action import Action
@@ -1063,9 +1067,17 @@ def __init__(self):
10631067
10641068 sage: QQbar.category() # indirect doctest
10651069 Category of infinite fields
1070+
1071+ Coercions::
1072+
1073+ sage: AA.has_coerce_map_from(ZZ)
1074+ True
1075+ sage: AA.has_coerce_map_from(int)
1076+ True
10661077 """
10671078 from sage .categories .fields import Fields
10681079 AlgebraicField_common .__init__ (self , self , ('x' ,), normalize = False , category = Fields ().Infinite ())
1080+ self ._populate_coercion_lists_ ([ZZ , QQ ])
10691081
10701082 def _element_constructor_ (self , x ):
10711083 r"""
@@ -1157,8 +1169,6 @@ def _coerce_map_from_(self, from_par):
11571169
11581170 TESTS::
11591171
1160- sage: AA.has_coerce_map_from(ZZ) # indirect doctest
1161- True
11621172 sage: K.<a> = QuadraticField(7, embedding=AA(7).sqrt()); AA.has_coerce_map_from(K)
11631173 True
11641174 sage: a in AA
@@ -1167,9 +1177,23 @@ def _coerce_map_from_(self, from_par):
11671177 5.645751311064590?
11681178 sage: AA.has_coerce_map_from(SR)
11691179 False
1180+
1181+ sage: K = NumberField(x^3 - 2, 'a', embedding=2.**(1/3))
1182+ sage: AA.has_coerce_map_from(K)
1183+ True
1184+ sage: K.<s> = QuadraticField(3, embedding=-2.)
1185+ sage: s + AA(1)
1186+ -0.732050807568878?
1187+ sage: K.<s> = QuadraticField(3, embedding=2.)
1188+ sage: s + AA(1)
1189+ 2.732050807568878?
1190+ sage: K.<s> = QuadraticField(-5)
1191+ sage: AA.has_coerce_map_from(K)
1192+ False
11701193 """
1171- return (from_par is ZZ or from_par is QQ
1172- or from_par is AA )
1194+ if isinstance (from_par , sage .rings .number_field .number_field_base .NumberField ):
1195+ emb = from_par .coerce_embedding ()
1196+ return emb is not None and parent_is_real_numerical (emb .codomain ())
11731197
11741198 def completion (self , p , prec , extras = {}):
11751199 r"""
@@ -1497,9 +1521,15 @@ def __init__(self):
14971521
14981522 sage: QQbar._repr_option('element_is_atomic')
14991523 False
1524+
1525+ sage: QQbar.has_coerce_map_from(ZZ)
1526+ True
1527+ sage: QQbar.has_coerce_map_from(int)
1528+ True
15001529 """
15011530 from sage .categories .fields import Fields
15021531 AlgebraicField_common .__init__ (self , AA , ('I' ,), normalize = False , category = Fields ().Infinite ())
1532+ self ._populate_coercion_lists_ ([ZZ , QQ ])
15031533
15041534 def _element_constructor_ (self , x ):
15051535 """
@@ -1565,17 +1595,28 @@ def _coerce_map_from_(self, from_par):
15651595
15661596 TESTS::
15671597
1568- sage: QQbar.has_coerce_map_from(ZZ) # indirect doctest
1569- True
15701598 sage: QQbar.has_coerce_map_from(AA)
15711599 True
15721600 sage: QQbar.has_coerce_map_from(CC)
15731601 False
15741602 sage: QQbar.has_coerce_map_from(SR)
15751603 False
1604+
1605+ sage: i + QQbar(2)
1606+ I + 2
1607+ sage: K.<ii> = QuadraticField(-1, embedding=ComplexField(13)(0,-1))
1608+ sage: ii + QQbar(2)
1609+ -I + 2
1610+
1611+ sage: L.<a> = QuadraticField(-1, embedding=Zp(5).teichmuller(2))
1612+ sage: QQbar.has_coerce_map_from(L)
1613+ False
15761614 """
1577- return (from_par is ZZ or from_par is QQ
1578- or from_par is AA or from_par is QQbar )
1615+ if from_par is AA :
1616+ return True
1617+ if isinstance (from_par , sage .rings .number_field .number_field_base .NumberField ):
1618+ emb = from_par .coerce_embedding ()
1619+ return emb is not None and parent_is_numerical (emb .codomain ())
15791620
15801621 def completion (self , p , prec , extras = {}):
15811622 r"""
@@ -3453,10 +3494,11 @@ def __init__(self, parent, x):
34533494 self ._descr = ANRational (x )
34543495 elif isinstance (x , ANDescr ):
34553496 self ._descr = x
3456- elif parent is QQbar and \
3457- isinstance (x , NumberFieldElement_quadratic ) and \
3458- list (x .parent ().polynomial ()) == [1 , 0 , 1 ]:
3459- self ._descr = ANExtensionElement (QQbar_I_generator , QQbar_I_nf (x .list ()))
3497+ elif parent is QQbar and isinstance (x , NumberFieldElement_gaussian ):
3498+ if x .parent ()._standard_embedding :
3499+ self ._descr = ANExtensionElement (QQbar_I_generator , QQbar_I_nf (x .list ()))
3500+ else :
3501+ self ._descr = ANExtensionElement (QQbar_I_generator , QQbar_I_nf ([x [0 ], - x [1 ]]))
34603502 else :
34613503 raise TypeError ("Illegal initializer for algebraic number" )
34623504
0 commit comments