[locale.general] (original) (raw)

28 Text processing library [text]

28.3 Localization library [localization]

28.3.3 Locales [locales]

28.3.3.1 Class locale [locale]

28.3.3.1.1 General [locale.general]

namespace std { class locale { public: class facet;class id;using category = int;static const category none = 0, collate = 0x010, ctype = 0x020, monetary = 0x040, numeric = 0x080, time = 0x100, messages = 0x200, all = collate | ctype | monetary | numeric | time | messages; locale() noexcept; locale(const locale& other) noexcept;explicit locale(const char* std_name);explicit locale(const string& std_name); locale(const locale& other, const char* std_name, category); locale(const locale& other, const string& std_name, category);template<class Facet> locale(const locale& other, Facet* f); locale(const locale& other, const locale& one, category);~locale(); const locale& operator=(const locale& other) noexcept;template<class Facet> locale combine(const locale& other) const; string name() const; text_encoding encoding() const;bool operator==(const locale& other) const;template<class charT, class traits, class Allocator> bool operator()(const basic_string<charT, traits, Allocator>& s1,const basic_string<charT, traits, Allocator>& s2) const;static locale global(const locale&);static const locale& classic();};}

Class locale implements a type-safe polymorphic set of facets, indexed by facet type.

In other words, a facet has a dual role: in one sense, it's just a class interface; at the same time, it's an index into a locale's set of facets.

Access to the facets of a locale is via two function templates,use_facet<> and has_facet<>.

[Example 1:

An iostream operator<< can be implemented as:215

template<class charT, class traits>basic_ostream<charT, traits>& operator<< (basic_ostream<charT, traits>& s, Date d) { typename basic_ostream<charT, traits>::sentry cerberos(s);if (cerberos) { tm tmbuf; d.extract(tmbuf);bool failed = use_facet<time_put<charT, ostreambuf_iterator<charT, traits>>>( s.getloc()).put(s, s, s.fill(), &tmbuf, 'x').failed();if (failed) s.setstate(s.badbit); } return s;} — _end example_]

In the call to use_facet<Facet>(loc), the type argument chooses a facet, making available all members of the named type.

If Facet is not present in a locale, it throws the standard exception bad_cast.

A C++ program can check if a locale implements a particular facet with the function template has_facet<Facet>().

User-defined facets may be installed in a locale, and used identically as may standard facets.

[Note 1:

All locale semantics are accessed viause_facet<> and has_facet<>, except that:

— _end note_]

Once a facet reference is obtained from a locale object by calling use_facet<>, that reference remains usable, and the results from member functions of it may be cached and re-used, as long as some locale object refers to that facet.

In successive calls to a locale facet member function on a facet object installed in the same locale, the returned result shall be identical.

A locale constructed from a name string (such as "POSIX"), or from parts of two named locales, has a name; all others do not.

Named locales may be compared for equality; an unnamed locale is equal only to (copies of) itself.

For an unnamed locale, locale​::​name() returns the string "*".

Whether there is one global locale object for the entire program or one global locale object per thread is implementation-defined.

Implementations should provide one global locale object per thread.

If there is a single global locale object for the entire program, implementations are not required to avoid data races on it ([res.on.data.races]).