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;
basic_string<char> name() const;
bool operator==(const locale& other) 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: An iostream
operator<<
might be implemented as:
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) {
ios_base::iostate err = ios_base::iostate::goodbit;
tm tmbuf; d.extract(tmbuf);
use_facet<time_put<charT, ostreambuf_iterator<charT, traits>> >(
s.getloc()).put(s, s, s.fill(), err, &tmbuf, 'x');
s.setstate(err); }
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 (
[facets.examples])
.[
Note: All locale semantics are accessed via
use_facet<>
and
has_facet<>,
except that:
A member operator template
operator()(const basic_string<C, T, A>&, const basic_string<C, T, A>&)
is provided so that a locale may be used as a predicate argument to
the standard collections, to collate strings
.Convenient global interfaces are provided for traditional
ctype
functions such as
isdigit()
and
isspace(),
so that given a locale
object
loc a C++ program can call
isspace(c, loc).
—
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])
.using category = int;
Valid
category
values include the
locale
member bitmask elements
collate,
ctype,
monetary,
numeric,
time,
and
messages,
each of which represents a single locale category
. In addition,
locale
member bitmask constant
none
is defined as zero and represents no category
. And
locale
member bitmask constant
all
is defined such that the expression
(collate | ctype | monetary | numeric | time | messages | all) == all
is
true,
and represents the union of all categories
. Further, the expression
(X | Y),
where
X
and
Y
each represent a single category, represents the union of the two categories
.locale
member functions expecting a
category
argument require one of the
category
values defined above, or the union of two or more such values
. Such a
category
value identifies a set of locale categories
. Each locale category,
in turn, identifies a set of locale facets, including at least those
shown in Table
64.Table
64 — Locale category facets
Category | Includes facets |
collate | collate<char>, collate<wchar_t> |
ctype | ctype<char>, ctype<wchar_t> |
| codecvt<char, char, mbstate_t> |
| codecvt<char16_t, char, mbstate_t> |
| codecvt<char32_t, char, mbstate_t> |
| codecvt<wchar_t, char, mbstate_t> |
monetary | moneypunct<char>, moneypunct<wchar_t> |
| moneypunct<char, true>, moneypunct<wchar_t, true> |
| money_get<char>, money_get<wchar_t> |
| money_put<char>, money_put<wchar_t> |
numeric | numpunct<char>, numpunct<wchar_t> |
| num_get<char>, num_get<wchar_t> |
| num_put<char>, num_put<wchar_t> |
time | time_get<char>, time_get<wchar_t> |
| time_put<char>, time_put<wchar_t> |
messages | messages<char>, messages<wchar_t> |
For any locale
loc
either constructed, or returned by
locale::classic(),
and any facet
Facet
shown in Table
64,
has_facet<Facet>(loc)
is
true. Each
locale
member function which takes a
locale::category
argument operates on the corresponding set of facets
.An implementation is required to provide those specializations for
facet templates identified as members of a category, and for those
shown in Table
65.Table
65 — Required specializations
Category | Includes facets |
collate | collate_byname<char>, collate_byname<wchar_t> |
ctype | ctype_byname<char>, ctype_byname<wchar_t> |
| codecvt_byname<char, char, mbstate_t> |
| codecvt_byname<char16_t, char, mbstate_t> |
| codecvt_byname<char32_t, char, mbstate_t> |
| codecvt_byname<wchar_t, char, mbstate_t> |
monetary | moneypunct_byname<char, International> |
| moneypunct_byname<wchar_t, International> |
| money_get<C, InputIterator> |
| money_put<C, OutputIterator> |
numeric | numpunct_byname<char>, numpunct_byname<wchar_t> |
| num_get<C, InputIterator>, num_put<C, OutputIterator> |
time | time_get<char, InputIterator> |
| time_get_byname<char, InputIterator> |
| time_get<wchar_t, InputIterator> |
| time_get_byname<wchar_t, InputIterator> |
| time_put<char, OutputIterator> |
| time_put_byname<char, OutputIterator> |
| time_put<wchar_t, OutputIterator> |
| time_put_byname<wchar_t, OutputIterator> |
messages | messages_byname<char>, messages_byname<wchar_t> |
The provided implementation of members of facets
num_get<charT>
and
num_put<charT>
calls
use_facet<F>(l)
only for facet
F
of types
numpunct<charT>
and
ctype<charT>,
and for locale
l
the value obtained
by calling member
getloc()
on the
ios_base&
argument to these functions
.In declarations of facets, a template parameter with name
InputIterator
or
OutputIterator
indicates the set of
all possible specializations on parameters that satisfy the
requirements of an Input Iterator or an Output Iterator, respectively (
[iterator.requirements])
. A template parameter with name
C
represents the set
of types containing
char,
wchar_t, and any other
implementation-defined
character types that satisfy
the requirements for a character on which any of the iostream
components can be instantiated
. A template parameter with name
International
represents the set of all possible specializations on a bool parameter
.
namespace std {
class locale::facet {
protected:
explicit facet(size_t refs = 0);
virtual ~facet();
facet(const facet&) = delete;
void operator=(const facet&) = delete;
};
}
Class
facet is the base class for locale feature sets
. A class is a
facet
if it is publicly derived from another facet, or
if it is a class derived from
locale::facet and
contains a publicly accessible declaration as follows:
static ::std::locale::id id;
Template parameters in this Clause which are required to be facets are those named
Facet
in declarations
. A program that passes a type that is
not
a facet, or a type that refers to a volatile-qualified facet, as an
(explicit or deduced) template parameter to a locale
function expecting a facet, is ill-formed
. A const-qualified facet is a
valid template argument to any locale function that expects a Facet template
parameter
.The
refs
argument to the constructor is used for lifetime management
. For
refs == 0,
the implementation performs
delete static_cast<locale::facet*>(f)
(where
f
is a pointer to the facet) when the last
locale
object containing the facet is destroyed;
for
refs == 1,
the implementation never destroys the facet
.Constructors of all
facets defined in this Clause take such an argument and pass it
along to their
facet
base class constructor
. All one-argument constructors defined
in this Clause are
explicit,
preventing their participation in automatic conversions
.For some standard facets a standard
“
…_byname”
class, derived from it, implements the virtual function semantics
equivalent to that facet of the locale constructed by
locale(const char*)
with the same name
. Each such facet provides a constructor that takes a
const char*
argument, which names the locale, and a
refs
argument, which is passed to the base class constructor
. Each such facet also provides a constructor that takes a
string argument
str and a
refs
argument, which has the same effect as calling the first constructor with the
two arguments
str.c_str() and
refs. If there is no
“
…_byname”
version of a facet, the base class implements named locale
semantics itself by reference to other facets
.
namespace std {
class locale::id {
public:
id();
void operator=(const id&) = delete;
id(const id&) = delete;
};
}
The class
locale::id provides identification of a locale facet
interface, used as an index for lookup
and to encapsulate initialization
.[
Note: Because facets are used by iostreams, potentially while static constructors are
running, their initialization cannot depend on programmed static
initialization
. One initialization strategy is for
locale
to initialize each facet's
id
member the first time an instance of the facet is installed into a locale
. —
end note ]
locale() noexcept;
Default constructor: a snapshot of the current global locale
.Effects:
Constructs a copy of the argument last passed to
locale::global(locale&),
if it has been called; else, the resulting facets have virtual
function semantics identical to those of
locale::classic(). [
Note: This constructor is commonly used as the default value for arguments
of functions that take a
const locale&
argument
. —
end note ]
locale(const locale& other) noexcept;
Effects:
Constructs a locale which is a copy of
other. explicit locale(const char* std_name);
Effects:
Constructs a locale using standard C locale names, e.g.,
"POSIX". The resulting locale implements semantics defined to be associated
with that name
.Throws:
runtime_error
if the argument is not valid, or is null
. Remarks:
The set of valid string argument values is
"C",
"",
and any
implementation-defined values
. explicit locale(const string& std_name);
Effects: The same as
locale(std_name.c_str()). locale(const locale& other, const char* std_name, category);
Effects:
Constructs a locale as a copy of
other
except for the facets identified by the
category
argument, which instead implement the same semantics as
locale(std_name). Throws:
runtime_error
if the argument is not valid, or is null
. Remarks:
The locale has a name if and only if
other
has a name
. locale(const locale& other, const string& std_name, category cat);
Effects: The same as
locale(other, std_name.c_str(), cat). template <class Facet> locale(const locale& other, Facet* f);
Effects:
Constructs a locale incorporating all facets from the first
argument except that of type
Facet,
and installs the second argument as the remaining facet
. If
f
is null, the resulting object is a copy of
other.Remarks:
The resulting locale has no name
. locale(const locale& other, const locale& one, category cats);
Effects:
Constructs a locale incorporating all facets from the first argument
except those that implement
cats,
which are instead incorporated from the second argument
. Remarks:
The resulting locale has a name if and only if the first two arguments
have names
. const locale& operator=(const locale& other) noexcept;
Effects:
Creates a copy of
other, replacing the current value
. ~locale();
A non-virtual destructor that throws no exceptions
.template <class Facet> locale combine(const locale& other) const;
Effects:
Constructs a locale incorporating
all facets from
*this
except for that one facet of
other
that is identified by
Facet. Returns:
The newly created locale
. Throws:
runtime_error
if
has_facet<Facet>(other)
is
false. Remarks:
The resulting locale has no name
. basic_string<char> name() const;
Returns:
The name of
*this,
if it has one; otherwise, the string
"*". bool operator==(const locale& other) const;
Returns:
true
if both arguments are the same locale, or one is a copy of the
other, or each has a name and the names are identical;
false
otherwise
. bool operator!=(const locale& other) const;
Returns: !(*this == other). template <class charT, class traits, class Allocator>
bool operator()(const basic_string<charT, traits, Allocator>& s1,
const basic_string<charT, traits, Allocator>& s2) const;
Effects:
Compares two strings according to the
collate<charT>
facet
. Remarks:
This member operator template (and therefore
locale
itself) satisfies requirements for a comparator predicate template argument
(Clause
[algorithms]) applied to strings
. Returns:
use_facet<collate<charT>>(*this).compare(s1.data(), s1.data() + s1.size(),
s2.data(), s2.data() + s2.size()) < 0
[
Example: A vector of strings
v
can be collated according to collation rules in locale
loc
simply by (
[alg.sort],
[vector]):
std::sort(v.begin(), v.end(), loc);
—
end example ]
static locale global(const locale& loc);
Sets the global locale to its argument
.Effects:
Causes future calls to the constructor
locale()
to return a copy of the argument
. If the argument has a name, does
setlocale(LC_ALL, loc.name().c_str());
otherwise, the effect on the C locale, if any, is
implementation-defined
. No library function other than
locale::global()
shall affect the value returned by
locale(). [
Note: See
[c.locales] for data race considerations when
setlocale is invoked
. —
end note ]
Returns:
The previous value of
locale(). static const locale& classic();
Returns:
A locale that implements the classic
"C" locale semantics, equivalent
to the value
locale("C"). Remarks:
This locale, its facets, and their member functions, do not change
with time
. template <class charT> bool isspace (charT c, const locale& loc);
template <class charT> bool isprint (charT c, const locale& loc);
template <class charT> bool iscntrl (charT c, const locale& loc);
template <class charT> bool isupper (charT c, const locale& loc);
template <class charT> bool islower (charT c, const locale& loc);
template <class charT> bool isalpha (charT c, const locale& loc);
template <class charT> bool isdigit (charT c, const locale& loc);
template <class charT> bool ispunct (charT c, const locale& loc);
template <class charT> bool isxdigit(charT c, const locale& loc);
template <class charT> bool isalnum (charT c, const locale& loc);
template <class charT> bool isgraph (charT c, const locale& loc);
template <class charT> bool isblank (charT c, const locale& loc);
Each of these functions
isF
returns the result of the expression:
use_facet<ctype<charT>>(loc).is(ctype_base::F, c)
where
F is the
ctype_base::mask
value corresponding to that function (
[category.ctype])
.template <class charT> charT toupper(charT c, const locale& loc);
Returns:
use_facet<ctype<charT>>(loc).toupper(c). template <class charT> charT tolower(charT c, const locale& loc);
Returns:
use_facet<ctype<charT>>(loc).tolower(c).