I understand that the statement "when python starts, it runs using the C locale..." should not be correct anymore (and the doc should then be updated), but in fact this statement is still true on the systems I tested; only, the output of locale.getlocale() at start is in contradiction with the locale really set in fact.
It looks like the setting done by setlocale(LC_ALL, "") at an early stage is lost at some point (only locale.getlocale() seems to "remember" it).
For instance, my box locale is 'fr_FR.UTF-8', so the decimal point is a comma, but when starting python 3.7:
>>> import locale
>>> locale.str(2.4)
'2.4' # Wrong: if the locale in use is 'fr_FR.UTF-8', then '2,4' is expected instead
>>> locale.getlocale()
('fr_FR', 'UTF-8')
>>> locale.localeconv()
{'int_curr_symbol': '', 'currency_symbol': '', 'mon_decimal_point': '', 'mon_thousands_sep': '', 'mon_grouping': [], 'positive_sign': '', 'negative_sign': '', 'int_frac_digits': 127, 'frac_digits': 127, 'p_cs_precedes': 127, 'p_sep_by_space': 127, 'n_cs_precedes': 127, 'n_sep_by_space': 127, 'p_sign_posn': 127, 'n_sign_posn': 127, 'decimal_point': '.', 'thousands_sep': '', 'grouping': []}
>>>
Note that the output of localeconv() does match C locale, not 'fr_FR.UTF-8'.
Compare this with the outputs of locale.str() and locale.localeconv() when the locale is explicitly set at start:
>>> import locale
>>> locale.setlocale(locale.LC_ALL, '')
'LC_CTYPE=fr_FR.utf8;LC_NUMERIC=fr_FR.UTF-8;LC_TIME=fr_FR.UTF-8;LC_COLLATE=fr_FR.utf8;LC_MONETARY=fr_FR.UTF-8;LC_MESSAGES=fr_FR.utf8;LC_PAPER=fr_FR.UTF-8;LC_NAME=fr_FR.UTF-8;LC_ADDRESS=fr_FR.UTF-8;LC_TELEPHONE=fr_FR.UTF-8;LC_MEASUREMENT=fr_FR.UTF-8;LC_IDENTIFICATION=fr_FR.UTF-8'
>>> locale.str(2.4)
'2,4' # Correct!
>>> locale.localeconv() # Output of localeconv() does match 'fr_FR.UTF-8' locale
{'int_curr_symbol': 'EUR ', 'currency_symbol': '€', 'mon_decimal_point': ',', 'mon_thousands_sep': '\u202f', 'mon_grouping': [3, 0], 'positive_sign': '', 'negative_sign': '-', 'int_frac_digits': 2, 'frac_digits': 2, 'p_cs_precedes': 0, 'p_sep_by_space': 1, 'n_cs_precedes': 0, 'n_sep_by_space': 1, 'p_sign_posn': 1, 'n_sign_posn': 1, 'decimal_point': ',', 'thousands_sep': '\u202f', 'grouping': [3, 0]}
>>>
Maybe the title of this issue should be turned to "at start, the C locale is in use in spite of locale.getlocale()'s output (python3 on linux)"?
As to the behaviour on Windows, I guess this is another topic (locales belonging to another world on Windows)... but it may be interesting to note that it complies with the current documentation: at start python 3.6 also uses the C locale, and the output of locale.getlocale() is consistent with that. Here is a test on Windows 10:
Python 3.6.3 (v3.6.3:2c5fed8, Oct 3 2017, 18:11:49) [MSC v.1900 64 bit (AMD64)] on win32
>>> import locale
>>> locale.getlocale()
(None, None)
>>> locale.localeconv()
{'decimal_point': '.', 'thousands_sep': '', 'grouping': [], 'int_curr_symbol': '', 'currency_symbol': '', 'mon_decimal_point': '', 'mon_thousands_sep': '', 'mon_grouping': [], 'positive_sign': '', 'negative_sign': '', 'int_frac_digits': 127, 'frac_digits': 127, 'p_cs_precedes': 127, 'p_sep_by_space': 127, 'n_cs_precedes': 127, 'n_sep_by_space': 127, 'p_sign_posn': 127, 'n_sign_posn': 127}
>>> locale.str(2.4)
'2.4'
>>> locale.getdefaultlocale()
('fr_FR', 'cp1252') |