File Doc/library/locale.rst changed (mode: 100644) (index 5aaf4a398f..181f534abe) |
... |
... |
The :mod:`locale` module defines the following exception and functions: |
352 |
352 |
sequence of strings. |
sequence of strings. |
353 |
353 |
|
|
354 |
354 |
|
|
355 |
|
.. function:: format(format, val, grouping=False, monetary=False) |
|
|
355 |
|
.. function:: format_string(format, val, grouping=False, monetary=False) |
356 |
356 |
|
|
357 |
357 |
Formats a number *val* according to the current :const:`LC_NUMERIC` setting. |
Formats a number *val* according to the current :const:`LC_NUMERIC` setting. |
358 |
358 |
The format follows the conventions of the ``%`` operator. For floating point |
The format follows the conventions of the ``%`` operator. For floating point |
|
... |
... |
The :mod:`locale` module defines the following exception and functions: |
362 |
362 |
If *monetary* is true, the conversion uses monetary thousands separator and |
If *monetary* is true, the conversion uses monetary thousands separator and |
363 |
363 |
grouping strings. |
grouping strings. |
364 |
364 |
|
|
365 |
|
Please note that this function will only work for exactly one %char specifier. |
|
366 |
|
For whole format strings, use :func:`format_string`. |
|
|
365 |
|
Processes formatting specifiers as in ``format % val``, but takes the current |
|
366 |
|
locale settings into account. |
367 |
367 |
|
|
|
368 |
|
.. versionchanged:: 3.7 |
|
369 |
|
The *monetary* keyword parameter was added. |
368 |
370 |
|
|
369 |
|
.. function:: format_string(format, val, grouping=False) |
|
370 |
371 |
|
|
371 |
|
Processes formatting specifiers as in ``format % val``, but takes the current |
|
372 |
|
locale settings into account. |
|
|
372 |
|
.. function:: format(format, val, grouping=False, monetary=False) |
|
373 |
|
|
|
374 |
|
Please note that this function works like format_string but will only work |
|
375 |
|
for exactly one %char specifier. |
|
376 |
|
|
|
377 |
|
For whole format strings, use :func:`format_string`. |
|
378 |
|
|
|
379 |
|
.. deprecated:: 3.7 |
|
380 |
|
Use :meth:`format_string` instead |
373 |
381 |
|
|
374 |
382 |
|
|
375 |
383 |
.. function:: currency(val, symbol=True, grouping=False, international=False) |
.. function:: currency(val, symbol=True, grouping=False, international=False) |
File Doc/whatsnew/3.7.rst changed (mode: 100644) (index b69f452b13..8f0962162c) |
... |
... |
Other Language Changes |
76 |
76 |
====================== |
====================== |
77 |
77 |
|
|
78 |
78 |
* More than 255 arguments can now be passed to a function, and a function can |
* More than 255 arguments can now be passed to a function, and a function can |
79 |
|
now have more than 255 parameters. |
|
80 |
|
(Contributed by Serhiy Storchaka in :issue:`12844` and :issue:`18896`.) |
|
|
79 |
|
now have more than 255 parameters. (Contributed by Serhiy Storchaka in |
|
80 |
|
:issue:`12844` and :issue:`18896`.) |
81 |
81 |
|
|
82 |
82 |
* :meth:`bytes.fromhex` and :meth:`bytearray.fromhex` now ignore all ASCII |
* :meth:`bytes.fromhex` and :meth:`bytearray.fromhex` now ignore all ASCII |
83 |
|
whitespace, not only spaces. |
|
84 |
|
(Contributed by Robert Xiao in :issue:`28927`.) |
|
|
83 |
|
whitespace, not only spaces. (Contributed by Robert Xiao in :issue:`28927`.) |
85 |
84 |
|
|
86 |
85 |
* :exc:`ImportError` now displays module name and module ``__file__`` path when |
* :exc:`ImportError` now displays module name and module ``__file__`` path when |
87 |
|
``from ... import ...`` fails. |
|
88 |
|
(Contributed by Matthias Bussonnier in :issue:`29546`.) |
|
|
86 |
|
``from ... import ...`` fails. (Contributed by Matthias Bussonnier in :issue:`29546`.) |
89 |
87 |
|
|
90 |
88 |
|
|
91 |
89 |
New Modules |
New Modules |
|
... |
... |
New Modules |
97 |
95 |
Improved Modules |
Improved Modules |
98 |
96 |
================ |
================ |
99 |
97 |
|
|
|
98 |
|
locale |
|
99 |
|
------ |
|
100 |
|
|
|
101 |
|
Added another argument *monetary* in :meth:`format_string` of :mod:`locale`. |
|
102 |
|
If *monetary* is true, the conversion uses monetary thousands separator and |
|
103 |
|
grouping strings. (Contributed by Garvit in :issue:`10379`.) |
|
104 |
|
|
100 |
105 |
os |
os |
101 |
106 |
-- |
-- |
102 |
107 |
|
|
103 |
|
Added support for :class:`bytes` paths in :func:`~os.fwalk`. |
|
104 |
|
(Contributed by Serhiy Storchaka in :issue:`28682`.) |
|
|
108 |
|
Added support for :class:`bytes` paths in :func:`~os.fwalk`. (Contributed by |
|
109 |
|
Serhiy Storchaka in :issue:`28682`.) |
105 |
110 |
|
|
106 |
111 |
unittest.mock |
unittest.mock |
107 |
112 |
------------- |
------------- |
108 |
113 |
|
|
109 |
114 |
The :const:`~unittest.mock.sentinel` attributes now preserve their identity |
The :const:`~unittest.mock.sentinel` attributes now preserve their identity |
110 |
|
when they are :mod:`copied <copy>` or :mod:`pickled <pickle>`. |
|
111 |
|
(Contributed by Serhiy Storchaka in :issue:`20804`.) |
|
|
115 |
|
when they are :mod:`copied <copy>` or :mod:`pickled <pickle>`. (Contributed by |
|
116 |
|
Serhiy Storchaka in :issue:`20804`.) |
112 |
117 |
|
|
113 |
118 |
xmlrpc.server |
xmlrpc.server |
114 |
119 |
------------- |
------------- |
115 |
120 |
|
|
116 |
121 |
:meth:`register_function` of :class:`xmlrpc.server.SimpleXMLRPCDispatcher` and |
:meth:`register_function` of :class:`xmlrpc.server.SimpleXMLRPCDispatcher` and |
117 |
|
its subclasses can be used as a decorator. |
|
118 |
|
(Contributed by Xiang Zhang in :issue:`7769`.) |
|
|
122 |
|
its subclasses can be used as a decorator. (Contributed by Xiang Zhang in |
|
123 |
|
:issue:`7769`.) |
119 |
124 |
|
|
120 |
125 |
urllib.parse |
urllib.parse |
121 |
126 |
------------ |
------------ |
|
... |
... |
Optimizations |
130 |
135 |
|
|
131 |
136 |
* Added two new opcodes: ``LOAD_METHOD`` and ``CALL_METHOD`` to avoid |
* Added two new opcodes: ``LOAD_METHOD`` and ``CALL_METHOD`` to avoid |
132 |
137 |
instantiation of bound method objects for method calls, which results |
instantiation of bound method objects for method calls, which results |
133 |
|
in method calls being faster up to 20%. |
|
134 |
|
(Contributed by Yury Selivanov and INADA Naoki in :issue:`26110`.) |
|
|
138 |
|
in method calls being faster up to 20%. (Contributed by Yury Selivanov and |
|
139 |
|
INADA Naoki in :issue:`26110`.) |
135 |
140 |
|
|
136 |
141 |
* Fast implementation from standard C library is now used for functions |
* Fast implementation from standard C library is now used for functions |
137 |
142 |
:func:`~math.tgamma`, :func:`~math.lgamma`, :func:`~math.erf` and |
:func:`~math.tgamma`, :func:`~math.lgamma`, :func:`~math.erf` and |
138 |
|
:func:`~math.erfc` in the :mod:`math` module. |
|
139 |
|
(Contributed by Serhiy Storchaka in :issue:`26121`.) |
|
|
143 |
|
:func:`~math.erfc` in the :mod:`math` module. (Contributed by Serhiy |
|
144 |
|
Storchaka in :issue:`26121`.) |
140 |
145 |
|
|
141 |
146 |
|
|
142 |
147 |
Build and C API Changes |
Build and C API Changes |
|
... |
... |
Build and C API Changes |
154 |
159 |
``char *``. (Contributed by Serhiy Storchaka in :issue:`28761`.) |
``char *``. (Contributed by Serhiy Storchaka in :issue:`28761`.) |
155 |
160 |
|
|
156 |
161 |
* The result of :c:func:`PyUnicode_AsUTF8AndSize` and :c:func:`PyUnicode_AsUTF8` |
* The result of :c:func:`PyUnicode_AsUTF8AndSize` and :c:func:`PyUnicode_AsUTF8` |
157 |
|
is now of type ``const char *`` rather of ``char *``. |
|
158 |
|
(Contributed by Serhiy Storchaka in :issue:`28769`.) |
|
|
162 |
|
is now of type ``const char *`` rather of ``char *``. (Contributed by Serhiy |
|
163 |
|
Storchaka in :issue:`28769`.) |
159 |
164 |
|
|
160 |
165 |
* Added functions :c:func:`PySlice_Unpack` and :c:func:`PySlice_AdjustIndices`. |
* Added functions :c:func:`PySlice_Unpack` and :c:func:`PySlice_AdjustIndices`. |
161 |
166 |
(Contributed by Serhiy Storchaka in :issue:`27867`.) |
(Contributed by Serhiy Storchaka in :issue:`27867`.) |
|
... |
... |
Deprecated |
169 |
174 |
``0x03050400`` and ``0x03060000`` (not including) or ``0x03060100`` or |
``0x03050400`` and ``0x03060000`` (not including) or ``0x03060100`` or |
170 |
175 |
higher. (Contributed by Serhiy Storchaka in :issue:`27867`.) |
higher. (Contributed by Serhiy Storchaka in :issue:`27867`.) |
171 |
176 |
|
|
|
177 |
|
- Deprecated :meth:`format` from :mod:`locale`, use the :meth:`format_string` |
|
178 |
|
instead. (Contributed by Garvit in :issue:`10379`.) |
|
179 |
|
|
172 |
180 |
- Methods |
- Methods |
173 |
181 |
:meth:`MetaPathFinder.find_module() <importlib.abc.MetaPathFinder.find_module>` |
:meth:`MetaPathFinder.find_module() <importlib.abc.MetaPathFinder.find_module>` |
174 |
182 |
(replaced by |
(replaced by |
|
... |
... |
Deprecated |
181 |
189 |
by Matthias Bussonnier in :issue:`29576`) |
by Matthias Bussonnier in :issue:`29576`) |
182 |
190 |
|
|
183 |
191 |
- Using non-integer value for selecting a plural form in :mod:`gettext` is |
- Using non-integer value for selecting a plural form in :mod:`gettext` is |
184 |
|
now deprecated. It never correctly worked. |
|
185 |
|
(Contributed by Serhiy Storchaka in :issue:`28692`.) |
|
|
192 |
|
now deprecated. It never correctly worked. (Contributed by Serhiy Storchaka |
|
193 |
|
in :issue:`28692`.) |
186 |
194 |
|
|
187 |
195 |
|
|
188 |
196 |
Changes in the C API |
Changes in the C API |
|
... |
... |
Changes in the Python API |
229 |
237 |
|
|
230 |
238 |
* A format string argument for :meth:`string.Formatter.format` |
* A format string argument for :meth:`string.Formatter.format` |
231 |
239 |
is now :ref:`positional-only <positional-only_parameter>`. |
is now :ref:`positional-only <positional-only_parameter>`. |
232 |
|
Passing it as a keyword argument was deprecated in Python 3.5. |
|
233 |
|
(Contributed by Serhiy Storchaka in :issue:`29193`.) |
|
|
240 |
|
Passing it as a keyword argument was deprecated in Python 3.5. (Contributed |
|
241 |
|
by Serhiy Storchaka in :issue:`29193`.) |
234 |
242 |
|
|
235 |
243 |
* Attributes :attr:`~http.cookies.Morsel.key`, |
* Attributes :attr:`~http.cookies.Morsel.key`, |
236 |
244 |
:attr:`~http.cookies.Morsel.value` and |
:attr:`~http.cookies.Morsel.value` and |
|
... |
... |
Changes in the Python API |
244 |
252 |
``ClassDef`` AST nodes now have a new ``docstring`` field. |
``ClassDef`` AST nodes now have a new ``docstring`` field. |
245 |
253 |
The first statement in their body is not considered as a docstring |
The first statement in their body is not considered as a docstring |
246 |
254 |
anymore. ``co_firstlineno`` and ``co_lnotab`` of code object for class |
anymore. ``co_firstlineno`` and ``co_lnotab`` of code object for class |
247 |
|
and module are affected by this change. |
|
248 |
|
(Contributed by INADA Naoki and Eugene Toder in :issue:`29463`.) |
|
|
255 |
|
and module are affected by this change. (Contributed by INADA Naoki and |
|
256 |
|
Eugene Toder in :issue:`29463`.) |
249 |
257 |
|
|
250 |
258 |
* The *mode* argument of :func:`os.makedirs` no longer affects the file |
* The *mode* argument of :func:`os.makedirs` no longer affects the file |
251 |
259 |
permission bits of newly-created intermediate-level directories. |
permission bits of newly-created intermediate-level directories. |
File Lib/locale.py changed (mode: 100644) (index f8d1d78c36..50cd652574) |
... |
... |
import re |
17 |
17 |
import collections |
import collections |
18 |
18 |
from builtins import str as _builtin_str |
from builtins import str as _builtin_str |
19 |
19 |
import functools |
import functools |
|
20 |
|
import warnings |
20 |
21 |
|
|
21 |
22 |
# Try importing the _locale module. |
# Try importing the _locale module. |
22 |
23 |
# |
# |
|
... |
... |
def _strip_padding(s, amount): |
180 |
181 |
_percent_re = re.compile(r'%(?:\((?P<key>.*?)\))?' |
_percent_re = re.compile(r'%(?:\((?P<key>.*?)\))?' |
181 |
182 |
r'(?P<modifiers>[-#0-9 +*.hlL]*?)[eEfFgGdiouxXcrs%]') |
r'(?P<modifiers>[-#0-9 +*.hlL]*?)[eEfFgGdiouxXcrs%]') |
182 |
183 |
|
|
183 |
|
def format(percent, value, grouping=False, monetary=False, *additional): |
|
184 |
|
"""Returns the locale-aware substitution of a %? specifier |
|
185 |
|
(percent). |
|
186 |
|
|
|
187 |
|
additional is for format strings which contain one or more |
|
188 |
|
'*' modifiers.""" |
|
189 |
|
# this is only for one-percent-specifier strings and this should be checked |
|
190 |
|
match = _percent_re.match(percent) |
|
191 |
|
if not match or len(match.group())!= len(percent): |
|
192 |
|
raise ValueError(("format() must be given exactly one %%char " |
|
193 |
|
"format specifier, %s not valid") % repr(percent)) |
|
194 |
|
return _format(percent, value, grouping, monetary, *additional) |
|
195 |
|
|
|
196 |
184 |
def _format(percent, value, grouping=False, monetary=False, *additional): |
def _format(percent, value, grouping=False, monetary=False, *additional): |
197 |
185 |
if additional: |
if additional: |
198 |
186 |
formatted = percent % ((value,) + additional) |
formatted = percent % ((value,) + additional) |
|
... |
... |
def _format(percent, value, grouping=False, monetary=False, *additional): |
217 |
205 |
formatted = _strip_padding(formatted, seps) |
formatted = _strip_padding(formatted, seps) |
218 |
206 |
return formatted |
return formatted |
219 |
207 |
|
|
220 |
|
def format_string(f, val, grouping=False): |
|
|
208 |
|
def format_string(f, val, grouping=False, monetary=False): |
221 |
209 |
"""Formats a string in the same way that the % formatting would use, |
"""Formats a string in the same way that the % formatting would use, |
222 |
210 |
but takes the current locale into account. |
but takes the current locale into account. |
223 |
|
Grouping is applied if the third parameter is true.""" |
|
|
211 |
|
|
|
212 |
|
Grouping is applied if the third parameter is true. |
|
213 |
|
Conversion uses monetary thousands separator and grouping strings if |
|
214 |
|
forth parameter monetary is true.""" |
224 |
215 |
percents = list(_percent_re.finditer(f)) |
percents = list(_percent_re.finditer(f)) |
225 |
216 |
new_f = _percent_re.sub('%s', f) |
new_f = _percent_re.sub('%s', f) |
226 |
217 |
|
|
|
... |
... |
def format_string(f, val, grouping=False): |
230 |
221 |
if perc.group()[-1]=='%': |
if perc.group()[-1]=='%': |
231 |
222 |
new_val.append('%') |
new_val.append('%') |
232 |
223 |
else: |
else: |
233 |
|
new_val.append(format(perc.group(), val, grouping)) |
|
|
224 |
|
new_val.append(_format(perc.group(), val, grouping, monetary)) |
234 |
225 |
else: |
else: |
235 |
226 |
if not isinstance(val, tuple): |
if not isinstance(val, tuple): |
236 |
227 |
val = (val,) |
val = (val,) |
|
... |
... |
def format_string(f, val, grouping=False): |
244 |
235 |
new_val.append(_format(perc.group(), |
new_val.append(_format(perc.group(), |
245 |
236 |
val[i], |
val[i], |
246 |
237 |
grouping, |
grouping, |
247 |
|
False, |
|
|
238 |
|
monetary, |
248 |
239 |
*val[i+1:i+1+starcount])) |
*val[i+1:i+1+starcount])) |
249 |
240 |
i += (1 + starcount) |
i += (1 + starcount) |
250 |
241 |
val = tuple(new_val) |
val = tuple(new_val) |
251 |
242 |
|
|
252 |
243 |
return new_f % val |
return new_f % val |
253 |
244 |
|
|
|
245 |
|
def format(percent, value, grouping=False, monetary=False, *additional): |
|
246 |
|
"""Deprecated, use format_string instead.""" |
|
247 |
|
warnings.warn( |
|
248 |
|
"This method will be removed in a future version of Python." |
|
249 |
|
"Use 'locale.format_string()' instead.", |
|
250 |
|
DeprecationWarning, stacklevel=2 |
|
251 |
|
) |
|
252 |
|
|
|
253 |
|
match = _percent_re.match(percent) |
|
254 |
|
if not match or len(match.group())!= len(percent): |
|
255 |
|
raise ValueError(("format() must be given exactly one %%char " |
|
256 |
|
"format specifier, %s not valid") % repr(percent)) |
|
257 |
|
return _format(percent, value, grouping, monetary, *additional) |
|
258 |
|
|
254 |
259 |
def currency(val, symbol=True, grouping=False, international=False): |
def currency(val, symbol=True, grouping=False, international=False): |
255 |
260 |
"""Formats val according to the currency settings |
"""Formats val according to the currency settings |
256 |
261 |
in the current locale.""" |
in the current locale.""" |
|
... |
... |
def currency(val, symbol=True, grouping=False, international=False): |
262 |
267 |
raise ValueError("Currency formatting is not possible using " |
raise ValueError("Currency formatting is not possible using " |
263 |
268 |
"the 'C' locale.") |
"the 'C' locale.") |
264 |
269 |
|
|
265 |
|
s = format('%%.%if' % digits, abs(val), grouping, monetary=True) |
|
|
270 |
|
s = _format('%%.%if' % digits, abs(val), grouping, monetary=True) |
266 |
271 |
# '<' and '>' are markers if the sign must be inserted between symbol and value |
# '<' and '>' are markers if the sign must be inserted between symbol and value |
267 |
272 |
s = '<' + s + '>' |
s = '<' + s + '>' |
268 |
273 |
|
|
|
... |
... |
def currency(val, symbol=True, grouping=False, international=False): |
298 |
303 |
|
|
299 |
304 |
def str(val): |
def str(val): |
300 |
305 |
"""Convert float to string, taking the locale into account.""" |
"""Convert float to string, taking the locale into account.""" |
301 |
|
return format("%.12g", val) |
|
|
306 |
|
return _format("%.12g", val) |
302 |
307 |
|
|
303 |
308 |
def delocalize(string): |
def delocalize(string): |
304 |
309 |
"Parses a string as a normalized number according to the locale settings." |
"Parses a string as a normalized number according to the locale settings." |
|
... |
... |
def atoi(string): |
327 |
332 |
def _test(): |
def _test(): |
328 |
333 |
setlocale(LC_ALL, "") |
setlocale(LC_ALL, "") |
329 |
334 |
#do grouping |
#do grouping |
330 |
|
s1 = format("%d", 123456789,1) |
|
|
335 |
|
s1 = format_string("%d", 123456789,1) |
331 |
336 |
print(s1, "is", atoi(s1)) |
print(s1, "is", atoi(s1)) |
332 |
337 |
#standard formatting |
#standard formatting |
333 |
338 |
s1 = str(3.14) |
s1 = str(3.14) |
File Lib/test/test_locale.py changed (mode: 100644) (index 99fab58cb9..06d286622a) |
... |
... |
import unittest |
3 |
3 |
import locale |
import locale |
4 |
4 |
import sys |
import sys |
5 |
5 |
import codecs |
import codecs |
|
6 |
|
import warnings |
6 |
7 |
|
|
7 |
8 |
class BaseLocalizedTest(unittest.TestCase): |
class BaseLocalizedTest(unittest.TestCase): |
8 |
9 |
# |
# |
|
... |
... |
class EnUSNumberFormatting(BaseFormattingTest): |
197 |
198 |
self._test_format("%+10.f", -4200, grouping=0, out='-4200'.rjust(10)) |
self._test_format("%+10.f", -4200, grouping=0, out='-4200'.rjust(10)) |
198 |
199 |
self._test_format("%-10.f", 4200, grouping=0, out='4200'.ljust(10)) |
self._test_format("%-10.f", 4200, grouping=0, out='4200'.ljust(10)) |
199 |
200 |
|
|
|
201 |
|
def test_format_deprecation(self): |
|
202 |
|
with self.assertWarns(DeprecationWarning): |
|
203 |
|
locale.format("%-10.f", 4200, grouping=True) |
|
204 |
|
|
200 |
205 |
def test_complex_formatting(self): |
def test_complex_formatting(self): |
201 |
206 |
# Spaces in formatting string |
# Spaces in formatting string |
202 |
207 |
self._test_format_string("One million is %i", 1000000, grouping=1, |
self._test_format_string("One million is %i", 1000000, grouping=1, |
File Lib/test/test_types.py changed (mode: 100644) (index 4a9fcba526..67d3281f3e) |
... |
... |
class TypesTests(unittest.TestCase): |
381 |
381 |
|
|
382 |
382 |
for i in range(-10, 10): |
for i in range(-10, 10): |
383 |
383 |
x = 1234567890.0 * (10.0 ** i) |
x = 1234567890.0 * (10.0 ** i) |
384 |
|
self.assertEqual(locale.format('%g', x, grouping=True), format(x, 'n')) |
|
385 |
|
self.assertEqual(locale.format('%.10g', x, grouping=True), format(x, '.10n')) |
|
|
384 |
|
self.assertEqual(locale.format_string('%g', x, grouping=True), format(x, 'n')) |
|
385 |
|
self.assertEqual(locale.format_string('%.10g', x, grouping=True), format(x, '.10n')) |
386 |
386 |
|
|
387 |
387 |
@run_with_locale('LC_NUMERIC', 'en_US.UTF8') |
@run_with_locale('LC_NUMERIC', 'en_US.UTF8') |
388 |
388 |
def test_int__format__locale(self): |
def test_int__format__locale(self): |
|
... |
... |
class TypesTests(unittest.TestCase): |
390 |
390 |
|
|
391 |
391 |
x = 123456789012345678901234567890 |
x = 123456789012345678901234567890 |
392 |
392 |
for i in range(0, 30): |
for i in range(0, 30): |
393 |
|
self.assertEqual(locale.format('%d', x, grouping=True), format(x, 'n')) |
|
|
393 |
|
self.assertEqual(locale.format_string('%d', x, grouping=True), format(x, 'n')) |
394 |
394 |
|
|
395 |
395 |
# move to the next integer to test |
# move to the next integer to test |
396 |
396 |
x = x // 10 |
x = x // 10 |