blob: 4360c540693efbbb0b20e0c0ca7096dae1c01afd [file] [log] [blame]
Michael W. Hudsonba283e22005-05-27 15:23:20 +00001
2import unittest, struct
3from test import test_support
4
5class FormatFunctionsTestCase(unittest.TestCase):
6
7 def setUp(self):
8 self.save_formats = {'double':float.__getformat__('double'),
9 'float':float.__getformat__('float')}
10
11 def tearDown(self):
12 float.__setformat__('double', self.save_formats['double'])
13 float.__setformat__('float', self.save_formats['float'])
14
15 def test_getformat(self):
16 self.assert_(float.__getformat__('double') in
17 ['unknown', 'IEEE, big-endian', 'IEEE, little-endian'])
18 self.assert_(float.__getformat__('float') in
19 ['unknown', 'IEEE, big-endian', 'IEEE, little-endian'])
20 self.assertRaises(ValueError, float.__getformat__, 'chicken')
21 self.assertRaises(TypeError, float.__getformat__, 1)
22
23 def test_setformat(self):
24 for t in 'double', 'float':
25 float.__setformat__(t, 'unknown')
26 if self.save_formats[t] == 'IEEE, big-endian':
27 self.assertRaises(ValueError, float.__setformat__,
28 t, 'IEEE, little-endian')
29 elif self.save_formats[t] == 'IEEE, little-endian':
30 self.assertRaises(ValueError, float.__setformat__,
31 t, 'IEEE, big-endian')
32 else:
33 self.assertRaises(ValueError, float.__setformat__,
34 t, 'IEEE, big-endian')
35 self.assertRaises(ValueError, float.__setformat__,
36 t, 'IEEE, little-endian')
37 self.assertRaises(ValueError, float.__setformat__,
38 t, 'chicken')
39 self.assertRaises(ValueError, float.__setformat__,
40 'chicken', 'unknown')
41
Guido van Rossum2be161d2007-05-15 20:43:51 +000042BE_DOUBLE_INF = b'\x7f\xf0\x00\x00\x00\x00\x00\x00'
Guido van Rossum254348e2007-11-21 19:29:53 +000043LE_DOUBLE_INF = bytes(reversed(BE_DOUBLE_INF))
Guido van Rossum2be161d2007-05-15 20:43:51 +000044BE_DOUBLE_NAN = b'\x7f\xf8\x00\x00\x00\x00\x00\x00'
Guido van Rossum254348e2007-11-21 19:29:53 +000045LE_DOUBLE_NAN = bytes(reversed(BE_DOUBLE_NAN))
Michael W. Hudsonba283e22005-05-27 15:23:20 +000046
Guido van Rossum2be161d2007-05-15 20:43:51 +000047BE_FLOAT_INF = b'\x7f\x80\x00\x00'
Guido van Rossum254348e2007-11-21 19:29:53 +000048LE_FLOAT_INF = bytes(reversed(BE_FLOAT_INF))
Guido van Rossum2be161d2007-05-15 20:43:51 +000049BE_FLOAT_NAN = b'\x7f\xc0\x00\x00'
Guido van Rossum254348e2007-11-21 19:29:53 +000050LE_FLOAT_NAN = bytes(reversed(BE_FLOAT_NAN))
Michael W. Hudsonba283e22005-05-27 15:23:20 +000051
52# on non-IEEE platforms, attempting to unpack a bit pattern
53# representing an infinity or a NaN should raise an exception.
54
55class UnknownFormatTestCase(unittest.TestCase):
56 def setUp(self):
57 self.save_formats = {'double':float.__getformat__('double'),
58 'float':float.__getformat__('float')}
59 float.__setformat__('double', 'unknown')
60 float.__setformat__('float', 'unknown')
Tim Peters5d36a552005-06-03 22:40:27 +000061
Michael W. Hudsonba283e22005-05-27 15:23:20 +000062 def tearDown(self):
63 float.__setformat__('double', self.save_formats['double'])
64 float.__setformat__('float', self.save_formats['float'])
65
66 def test_double_specials_dont_unpack(self):
67 for fmt, data in [('>d', BE_DOUBLE_INF),
68 ('>d', BE_DOUBLE_NAN),
69 ('<d', LE_DOUBLE_INF),
70 ('<d', LE_DOUBLE_NAN)]:
71 self.assertRaises(ValueError, struct.unpack, fmt, data)
72
73 def test_float_specials_dont_unpack(self):
74 for fmt, data in [('>f', BE_FLOAT_INF),
75 ('>f', BE_FLOAT_NAN),
76 ('<f', LE_FLOAT_INF),
77 ('<f', LE_FLOAT_NAN)]:
78 self.assertRaises(ValueError, struct.unpack, fmt, data)
79
80
81# on an IEEE platform, all we guarantee is that bit patterns
82# representing infinities or NaNs do not raise an exception; all else
83# is accident (today).
Guido van Rossum04110fb2007-08-24 16:32:05 +000084# let's also try to guarantee that -0.0 and 0.0 don't get confused.
Michael W. Hudsonba283e22005-05-27 15:23:20 +000085
86class IEEEFormatTestCase(unittest.TestCase):
87 if float.__getformat__("double").startswith("IEEE"):
88 def test_double_specials_do_unpack(self):
89 for fmt, data in [('>d', BE_DOUBLE_INF),
90 ('>d', BE_DOUBLE_NAN),
91 ('<d', LE_DOUBLE_INF),
92 ('<d', LE_DOUBLE_NAN)]:
93 struct.unpack(fmt, data)
94
95 if float.__getformat__("float").startswith("IEEE"):
96 def test_float_specials_do_unpack(self):
97 for fmt, data in [('>f', BE_FLOAT_INF),
98 ('>f', BE_FLOAT_NAN),
99 ('<f', LE_FLOAT_INF),
100 ('<f', LE_FLOAT_NAN)]:
101 struct.unpack(fmt, data)
102
Guido van Rossum04110fb2007-08-24 16:32:05 +0000103 if float.__getformat__("double").startswith("IEEE"):
104 def test_negative_zero(self):
105 import math
106 def pos_pos():
107 return 0.0, math.atan2(0.0, -1)
108 def pos_neg():
109 return 0.0, math.atan2(-0.0, -1)
110 def neg_pos():
111 return -0.0, math.atan2(0.0, -1)
112 def neg_neg():
113 return -0.0, math.atan2(-0.0, -1)
114 self.assertEquals(pos_pos(), neg_pos())
115 self.assertEquals(pos_neg(), neg_neg())
116
Eric Smith8c663262007-08-25 02:26:07 +0000117class FormatTestCase(unittest.TestCase):
Eric Smith11fe3e02007-08-31 01:33:06 +0000118 def test_format(self):
Eric Smith8c663262007-08-25 02:26:07 +0000119 # these should be rewritten to use both format(x, spec) and
120 # x.__format__(spec)
121
122 self.assertEqual(format(0.0, 'f'), '0.000000')
123
124 # the default is 'g', except for empty format spec
125 self.assertEqual(format(0.0, ''), '0.0')
126 self.assertEqual(format(0.01, ''), '0.01')
127 self.assertEqual(format(0.01, 'g'), '0.01')
128
129 self.assertEqual(format(0, 'f'), '0.000000')
130
131 self.assertEqual(format(1.0, 'f'), '1.000000')
132 self.assertEqual(format(1, 'f'), '1.000000')
133
134 self.assertEqual(format(-1.0, 'f'), '-1.000000')
135 self.assertEqual(format(-1, 'f'), '-1.000000')
136
137 self.assertEqual(format( 1.0, ' f'), ' 1.000000')
138 self.assertEqual(format(-1.0, ' f'), '-1.000000')
139 self.assertEqual(format( 1.0, '+f'), '+1.000000')
140 self.assertEqual(format(-1.0, '+f'), '-1.000000')
141
142 # % formatting
143 self.assertEqual(format(-1.0, '%'), '-100.000000%')
144
145 # conversion to string should fail
146 self.assertRaises(ValueError, format, 3.0, "s")
147
Michael W. Hudsonba283e22005-05-27 15:23:20 +0000148
149def test_main():
150 test_support.run_unittest(
151 FormatFunctionsTestCase,
152 UnknownFormatTestCase,
Eric Smith8c663262007-08-25 02:26:07 +0000153 IEEEFormatTestCase,
154 FormatTestCase)
Michael W. Hudsonba283e22005-05-27 15:23:20 +0000155
156if __name__ == '__main__':
157 test_main()