You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
643 lines
20 KiB
643 lines
20 KiB
/***************************************************************************
|
|
*
|
|
* _locale.h - Declarations for the Standard Library locale classes
|
|
*
|
|
* This is an internal header file used to implement the C++ Standard
|
|
* Library. It should never be #included directly by a program.
|
|
*
|
|
* $Id: _locale.h 172106 2011-11-02 17:04:12Z statham $
|
|
*
|
|
***************************************************************************
|
|
*
|
|
* Copyright (c) 1994-2001 Rogue Wave Software, Inc. All Rights Reserved.
|
|
*
|
|
* This computer software is owned by Rogue Wave Software, Inc. and is
|
|
* protected by U.S. copyright laws and other laws and by international
|
|
* treaties. This computer software is furnished by Rogue Wave Software,
|
|
* Inc. pursuant to a written license agreement and may be used, copied,
|
|
* transmitted, and stored only in accordance with the terms of such
|
|
* license and with the inclusion of the above copyright notice. This
|
|
* computer software or any other copies thereof may not be provided or
|
|
* otherwise made available to any other person.
|
|
*
|
|
* U.S. Government Restricted Rights. This computer software is provided
|
|
* with Restricted Rights. Use, duplication, or disclosure by the
|
|
* Government is subject to restrictions as set forth in subparagraph (c)
|
|
* (1) (ii) of The Rights in Technical Data and Computer Software clause
|
|
* at DFARS 252.227-7013 or subparagraphs (c) (1) and (2) of the
|
|
* Commercial Computer Software--Restricted Rights at 48 CFR 52.227-19,
|
|
* as applicable. Manufacturer is Rogue Wave Software, Inc., 5500
|
|
* Flatiron Parkway, Boulder, Colorado 80301 USA.
|
|
*
|
|
**************************************************************************/
|
|
|
|
#ifndef _RWSTD_LOCALE_H_INCLUDED
|
|
#define _RWSTD_LOCALE_H_INCLUDED
|
|
|
|
|
|
#include <string>
|
|
#include <iosfwd>
|
|
|
|
#include <rw/_defs.h>
|
|
#include <rw/_error.h>
|
|
#include <rw/_locimp.h>
|
|
|
|
#include _RWSTD_CTIME
|
|
#include _RWSTD_CLOCALE
|
|
|
|
|
|
_RWSTD_NAMESPACE_BEGIN (std)
|
|
|
|
class _RWSTD_EXPORT locale;
|
|
|
|
template <class _CharT>
|
|
class collate;
|
|
|
|
|
|
#ifndef _RWSTD_NO_TEMPLATE_ON_RETURN_TYPE
|
|
|
|
template <class _Facet>
|
|
inline const _Facet& use_facet (const locale&);
|
|
|
|
template <class _Facet>
|
|
inline bool has_facet (const locale&) _THROWS (());
|
|
|
|
#else // if defined (_RWSTD_NO_TEMPLATE_ON_RETURN_TYPE)
|
|
|
|
template <class _Facet>
|
|
inline const _Facet& use_facet (const locale&, _Facet*);
|
|
|
|
template <class _Facet>
|
|
inline bool has_facet (const locale&, _Facet*) _THROWS (());
|
|
|
|
#endif // _RWSTD_NO_TEMPLATE_ON_RETURN_TYPE
|
|
|
|
_RWSTD_NAMESPACE_END // std
|
|
|
|
|
|
_RWSTD_NAMESPACE_BEGIN (std)
|
|
|
|
|
|
class _RWSTD_EXPORT locale
|
|
{
|
|
public:
|
|
class facet;
|
|
class id;
|
|
|
|
friend class facet;
|
|
friend class id;
|
|
|
|
typedef int category;
|
|
|
|
_RWSTD_STATIC_CONST (category, none = _RW::__rw_locale_imp::_C_none);
|
|
_RWSTD_STATIC_CONST (category, collate = _RW::__rw_locale_imp::_C_collate);
|
|
_RWSTD_STATIC_CONST (category, ctype = _RW::__rw_locale_imp::_C_ctype);
|
|
_RWSTD_STATIC_CONST (category, monetary = _RW::__rw_locale_imp::_C_monetary);
|
|
_RWSTD_STATIC_CONST (category, numeric = _RW::__rw_locale_imp::_C_numeric);
|
|
_RWSTD_STATIC_CONST (category, time = _RW::__rw_locale_imp::_C_time);
|
|
_RWSTD_STATIC_CONST (category, messages = _RW::__rw_locale_imp::_C_messages);
|
|
_RWSTD_STATIC_CONST (category, all = _RW::__rw_locale_imp::_C_all);
|
|
|
|
// The default constructor creates a copy of the current global locale,
|
|
// the locale specified in the most recent call to locale::global().
|
|
// If locale::global() has not been called, it is the classic "C" locale.
|
|
|
|
inline locale () _THROWS (());
|
|
|
|
// The copy constructor (and the assignment operator, below) can be used
|
|
// freely. Like a string, most of a locale's contents are in a separate,
|
|
// reference-counted implementation object, so copying and assigning
|
|
// locales/ has little overhead.
|
|
|
|
inline locale (const locale& __rhs) _THROWS (())
|
|
: _C_imp (__rhs._C_imp) {
|
|
_RWSTD_ATOMIC_PREINCREMENT (_C_imp->_C_ref_count, _C_imp->_C_mutex);
|
|
}
|
|
|
|
// The following constructor creates a locale composed of by-name facets
|
|
// and assigns it a name. The valid arguments are "", "C", and a set of
|
|
// strings defined by the compiler vendor. These cause the facets of
|
|
// the locale to be obtained, respectively, from the user's preferred
|
|
// locale, from the classic locale, or from the compiler's locale
|
|
// database. (In many cases, the preferred locale is specified by
|
|
// environment variables such as LANG or LC_ALL.) If the argument is
|
|
// not recognized, the constructor throws runtime_error.
|
|
|
|
_EXPLICIT locale (const char*);
|
|
|
|
// The following constructor copies its first argument except for
|
|
// the facets in the categories identified by the third argument,
|
|
// which are obtained by name using the second argument.
|
|
// Can throw runtime_error.
|
|
|
|
locale (const locale&, const char*, category);
|
|
|
|
// The following templatized constructor copies its first argument except
|
|
// the single _Facet of type _Facet
|
|
|
|
#ifndef _RWSTD_NO_MEMBER_TEMPLATES
|
|
|
|
template <class _Facet>
|
|
locale (const locale&, _Facet*);
|
|
|
|
#else
|
|
|
|
// If your compiler does not support member function templates, we provide
|
|
// the following work-around to let you accrete facets onto a locale.
|
|
// This constructor copies its first argument except for the single
|
|
// _Facet of the type of the second argument, for which it uses
|
|
// the second argument. To determine the type of the second argument,
|
|
// it calls the non-standard virtual method _C_get_id in the second
|
|
// argument. If you are creating your own _Facet types on a compiler
|
|
// that does not support member templates, you must code a _C_get_id
|
|
// member as follows in each new base class _Facet (i.e. in each _Facet
|
|
// class that has its own static member id of type locale::id):
|
|
//
|
|
// virtual locale::id &_C_get_id (void) const { return id; }
|
|
//
|
|
// See the _C_get_id members in the standard facets below for examples.
|
|
|
|
locale (const locale&, facet*);
|
|
|
|
#endif // _RWSTD_NO_MEMBER_TEMPLATES
|
|
|
|
// The following constructor copies its first argument except for
|
|
// the facets in the categories identified by the third argument,
|
|
// which are obtained from the second argument.
|
|
|
|
locale (const locale&, const locale&, category);
|
|
|
|
~locale () {
|
|
// HACK: _C_imp should normally never be 0; internally, though,
|
|
// it's set to 0 in locale::_C_make_facet to prevent a deadlock
|
|
if (_C_imp && 0 == _RWSTD_ATOMIC_PREDECREMENT (_C_imp->_C_ref_count,
|
|
_C_imp->_C_mutex))
|
|
delete _C_imp;
|
|
}
|
|
|
|
const locale& operator = (const locale&) _THROWS (());
|
|
|
|
// The following member function returns a copy of this locale (*this)
|
|
// except the single _Facet of type _Facet obtained from the other locale.
|
|
|
|
#ifndef _RWSTD_NO_MEMBER_TEMPLATES
|
|
#ifndef _RWSTD_NO_TEMPLATE_ON_RETURN_TYPE
|
|
|
|
template <class _Facet>
|
|
locale combine (const locale &__rhs) const {
|
|
// The cast from (const _Facet*) to (_Facet*) highlights a possible
|
|
// defect in the Standard ... see the issues list.
|
|
return locale (*this,
|
|
_RWSTD_CONST_CAST(_Facet*, &_USE_FACET (_Facet, __rhs)));
|
|
}
|
|
|
|
|
|
#endif // _RWSTD_NO_TEMPLATE_ON_RETURN_TYPE
|
|
#endif // _RWSTD_NO_MEMBER_TEMPLATES
|
|
|
|
// The following returns the locale name, or "*" if the locale is unnamed.
|
|
|
|
string name () const;
|
|
|
|
// Two locales are equal if they are the same object, or one is a copy
|
|
// of the other (i.e. they have the same implementation object),
|
|
// or both are named and their names are the same.
|
|
|
|
bool operator== (const locale &__rhs) const {
|
|
return this == &__rhs || _C_imp == __rhs._C_imp
|
|
|| name() != "*" && name () == __rhs.name();
|
|
}
|
|
|
|
bool operator != (const locale& __rhs) const {
|
|
return !(*this == __rhs);
|
|
}
|
|
|
|
// The following templatized operator () satisfies STL requirements for
|
|
// a comparator predicate template argument for comparing strings
|
|
// according to the collating sequence of the locale. It lets you use
|
|
// a locale directly as a comparator using syntax like
|
|
// sort(v.begin(), v.end(), loc),
|
|
// where v is a vector of some string type and loc is a locale.
|
|
|
|
#ifndef _RWSTD_NO_MEMBER_TEMPLATES
|
|
|
|
template <class _CharT, class _Traits, class _Allocator>
|
|
bool
|
|
operator() (const basic_string<_CharT, _Traits, _Allocator>& __x,
|
|
const basic_string<_CharT, _Traits, _Allocator>& __y) const;
|
|
|
|
#else // if defined (_RWSTD_NO_MEMBER_TEMPLATES)
|
|
|
|
bool operator() (const string &__x, const string &__y) const;
|
|
|
|
#ifndef _RWSTD_NO_WCHAR_T
|
|
|
|
bool operator() (const wstring &__x, const wstring &__y) const;
|
|
|
|
#endif // _RWSTD_NO_WCHAR_T
|
|
#endif // _RWSTD_NO_MEMBER_TEMPLATES
|
|
|
|
|
|
// Replaces the current global locale
|
|
static locale global (const locale&);
|
|
|
|
// Returns the classic "C" locale
|
|
static const locale& classic ();
|
|
|
|
// class _Facet -- base class for locale feature sets.
|
|
|
|
// Any class deriving from _Facet that wants to be perceived as a distinct
|
|
// _Facet, as opposed to a re-implementation of an existing _Facet, must
|
|
// declare a static member: static std::locale::id id;
|
|
|
|
class _RWSTD_EXPORT facet: public _RW::__rw_facet_base {
|
|
friend class _RW::__rw_locale_imp;
|
|
friend class locale;
|
|
|
|
protected:
|
|
|
|
_EXPLICIT facet (size_t __ref = 0, int __cat = 0)
|
|
: _RW::__rw_facet_base (__ref, __cat) { }
|
|
|
|
#ifdef _RWSTD_NO_MEMBER_TEMPLATES
|
|
virtual id &_C_get_id (void) const = 0;
|
|
#endif
|
|
|
|
private:
|
|
|
|
facet (const facet&); // not defined
|
|
void operator= (const facet&); // not defined
|
|
};
|
|
|
|
// class id -- _Facet type identifier.
|
|
|
|
// This is an implementation class. It is used internally as an index
|
|
// to find facets within a locale. Each distinct _Facet (i.e. each T
|
|
// that can be the parameter of a use_facet<_TypeT> call) has a unique
|
|
// static member of type locale::id named id. The class is made public
|
|
// to enable extension of the set of standard facets. Objects of this
|
|
// type don't need to be constructed or referenced in any other
|
|
// circumstances.
|
|
|
|
// the class must be `exported' in order for MSVC to collapse
|
|
// the static in _C_init into a single object if linking to a DLL
|
|
class _RWSTD_EXPORT id {
|
|
|
|
friend class locale;
|
|
|
|
_MUTABLE size_t _C_id; // unique id
|
|
|
|
void _C_init () const;
|
|
|
|
operator size_t () const {
|
|
return _C_id;
|
|
}
|
|
|
|
public:
|
|
id (): _C_id (0) { }
|
|
|
|
private:
|
|
id (const id&); // undefined
|
|
void operator= (const id&); // undefined
|
|
};
|
|
|
|
// Typedef for the implementation-defined call-back functions
|
|
// that must be passed to _C_make_facet (below).
|
|
typedef _RW::__rw_facet_maker_func __facet_maker_func;
|
|
|
|
// MT-safe std::use_facet<>() implementation
|
|
const facet& _C_use_facet (const id &__id, bool __implicit, category __cat,
|
|
__facet_maker_func __maker) const;
|
|
|
|
// same as above but not MT-safe
|
|
const facet& _C_unsafe_use_facet (const id &__id, bool __implicit,
|
|
category __cat,
|
|
__facet_maker_func __maker) const;
|
|
|
|
// The following function retrieves an implicit _Facet from a cache,
|
|
// or creates one if needed (via call to the passed call-back
|
|
// function), and makes it an explicit _Facet of the locale.
|
|
|
|
facet* _C_make_facet (const id &__id, bool __implicit,
|
|
category __cat, __facet_maker_func) const;
|
|
|
|
facet* _C_get_facet (const id &__id) const {
|
|
return _RWSTD_STATIC_CAST (facet*, _C_imp->_C_get_facet (__id));
|
|
}
|
|
|
|
|
|
void _C_install_facet (_RW::__rw_facet_base*, const id&) const;
|
|
|
|
private:
|
|
|
|
friend class _RW::__rw_locale_imp;
|
|
|
|
// Construct a locale from an implementation object.
|
|
_EXPLICIT locale (_RW::__rw_locale_imp*);
|
|
|
|
// Create initial implementation objects.
|
|
static void _C_init ();
|
|
|
|
// remove all facets satisfying the given category
|
|
inline void _C_remove_facets (category);
|
|
|
|
static _RW::__rw_locale_imp *_C_classic; // the classic "C" locale
|
|
static _RW::__rw_locale_imp *_C_native; // the native "C++" locale
|
|
static _RW::__rw_locale_imp *_C_global; // the global locale
|
|
|
|
_RW::__rw_locale_imp *_C_imp; // pointer to a ref counted implementation
|
|
};
|
|
|
|
|
|
#if defined (_RWSTD_MULTI_THREAD) && !defined (_RWSTD_NO_STATIC_MUTEX_INIT)
|
|
|
|
_RWSTD_NAMESPACE_END // std
|
|
|
|
_RWSTD_NAMESPACE_BEGIN (__rw)
|
|
|
|
// explicitly instantiated to work around a g++ 2.95.2 bug on COFF systems
|
|
// (such as IBM AIX or DEC OSF1) where it "forgets" to do so implicitly for
|
|
// explicitly initialized static data members
|
|
_RWSTD_INSTANTIATE_1 (class _RWSTD_EXPORT __rw_static_mutex<_STD::locale>);
|
|
|
|
_RWSTD_NAMESPACE_END // __rw
|
|
|
|
_RWSTD_NAMESPACE_BEGIN (std)
|
|
|
|
#endif // _RWSTD_MULTI_THREAD && !_RWSTD_NO_STATIC_MUTEX_INIT
|
|
|
|
|
|
// ----------------------------
|
|
// Class locale inline members.
|
|
// ----------------------------
|
|
|
|
|
|
// Private constructor for use by implementation, constructs a locale from
|
|
// a __rw_locale_imp implementation object.
|
|
inline locale::locale (_RW::__rw_locale_imp *__rhs)
|
|
: _C_imp (__rhs)
|
|
{
|
|
_RWSTD_ASSERT (0 != __rhs);
|
|
|
|
if (!_C_global)
|
|
_C_init ();
|
|
|
|
// no lock here to prevent a deadlock, called only from guarded contexts
|
|
++_C_imp->_C_ref_count;
|
|
}
|
|
|
|
|
|
// Default constructor, returns a copy of the current global locale.
|
|
inline locale::locale () _THROWS (())
|
|
{
|
|
if (!_C_global)
|
|
_C_init ();
|
|
|
|
_C_imp = _C_global;
|
|
|
|
_RWSTD_ASSERT (0 != _C_imp);
|
|
|
|
_RWSTD_ATOMIC_PREINCREMENT (_C_imp->_C_ref_count, _C_imp->_C_mutex);
|
|
}
|
|
|
|
|
|
#ifndef _RWSTD_NO_MEMBER_TEMPLATES
|
|
|
|
// Constructor to accrete or replace a single _Facet.
|
|
template <class _Facet>
|
|
inline locale::locale (const locale& __rhs, _Facet* __facet)
|
|
{
|
|
_RWSTD_ASSERT (0 != __rhs._C_imp);
|
|
|
|
_RWSTD_MT_GUARD (__rhs._C_imp->_C_mutex);
|
|
|
|
// Identical, EXCEPT no name -- so we can't just increment
|
|
// the ref count on the existing imp -- we need a new imp.
|
|
|
|
_C_imp = new _RW::__rw_locale_imp (*__rhs._C_imp, 0, 1);
|
|
|
|
if (__facet) {
|
|
_C_install_facet (__facet, _Facet::id);
|
|
}
|
|
}
|
|
|
|
|
|
// Operator () compares two strings according to the collate<_CharT> facet of
|
|
// the locale. It lets you use a locale object directly as a comparator
|
|
// predicate for strings in various algorithms. For instance, you can sort
|
|
// a vector<string> according to the collating sequence of a locale with an
|
|
// expression like: sort(v.begin(),v.end(),mylocale).
|
|
|
|
template <class _CharT, class _Traits, class _Allocator>
|
|
inline bool
|
|
locale::operator() (const basic_string<_CharT,_Traits,_Allocator>& __x,
|
|
const basic_string<_CharT,_Traits,_Allocator>& __y) const
|
|
{
|
|
return _USE_FACET (_STD::collate<_CharT>, *this)
|
|
.compare (__x.data (), __x.data () + __x.length (),
|
|
__y.data (), __y.data () + __y.length ()) < 0;
|
|
}
|
|
|
|
#else // if defined (_RWSTD_NO_MEMBER_TEMPLATES)
|
|
|
|
inline locale::locale (const locale& __rhs, facet* __facet):
|
|
_C_imp (0)
|
|
{
|
|
_RWSTD_MT_GUARD (__rhs._C_imp->_C_mutex);
|
|
|
|
_C_imp = new _RW::__rw_locale_imp (*__rhs._C_imp, 0, 1);
|
|
if (__facet)
|
|
_C_install_facet (__facet, __facet->_C_get_id ());
|
|
}
|
|
|
|
#endif // _RWSTD_NO_MEMBER_TEMPLATES
|
|
|
|
#ifdef _INLINE_WITH_STATICS
|
|
|
|
_INLINE_WITH_STATICS void locale::id::_C_init () const
|
|
{
|
|
// implicit initialization used to prevent a g++ 2.95.2 warning
|
|
// on Tru64: sorry: semantics of inline function static data are
|
|
// wrong (you'll wind up with multiple copies)
|
|
static size_t _C_id_gen /* = 0 */;
|
|
|
|
if (!_C_id)
|
|
_C_id = _RWSTD_ATOMIC_PREINCREMENT (_C_id_gen, false);
|
|
}
|
|
|
|
#endif // _INLINE_WITH_STATICS
|
|
|
|
|
|
inline const locale::facet&
|
|
locale::_C_use_facet (const id &__id, bool __implicit, category __cat,
|
|
__facet_maker_func __maker) const
|
|
{
|
|
_RWSTD_ASSERT (0 != _C_imp);
|
|
|
|
// not guarded (heavily used in iostreams)
|
|
const facet *__facet = _C_get_facet (__id);
|
|
|
|
// If facet is not explicitly present in locale yet, use private function
|
|
// locale::_C_make_facet to construct it or retrieve it from a cache,
|
|
// and install it in the locale. This function can throw bad_cast or
|
|
// other exceptions.
|
|
|
|
if (!__facet) {
|
|
_RWSTD_MT_GUARD (_C_imp->_C_mutex);
|
|
|
|
__facet = _C_make_facet (__id, __implicit, __cat, __maker);
|
|
}
|
|
|
|
_RWSTD_ASSERT (__facet);
|
|
|
|
return *__facet;
|
|
}
|
|
|
|
// same as above but not guarded; called during initialization
|
|
// of the num_get<> and num_put<> facets (this is a hack)
|
|
inline const locale::facet&
|
|
locale::_C_unsafe_use_facet (const id &__id, bool __implicit, category __cat,
|
|
__facet_maker_func __maker) const
|
|
{
|
|
_RWSTD_ASSERT (0 != _C_imp);
|
|
|
|
const facet *__facet = _C_get_facet (__id);
|
|
|
|
if (!__facet)
|
|
__facet = _C_make_facet (__id, __implicit, __cat, __maker);
|
|
|
|
_RWSTD_ASSERT (__facet);
|
|
|
|
return *__facet;
|
|
}
|
|
|
|
|
|
_RWSTD_NAMESPACE_END // std
|
|
|
|
|
|
_RWSTD_NAMESPACE_BEGIN (__rw)
|
|
|
|
// -------------------------------------------------------
|
|
// Implementation function template -- create_named_facet.
|
|
// -------------------------------------------------------
|
|
//
|
|
// The default for facets with no derived byname version is to create a _Facet
|
|
// with classic ("C") behavior, ignoring the passed name.
|
|
|
|
template <class _Facet>
|
|
inline _Facet*
|
|
__rw_create_named_facet (_Facet*, const char *__name, _RWSTD_C::size_t __ref)
|
|
{
|
|
_RWSTD_UNUSED (__name);
|
|
|
|
// 22.1.1.1.2, p1: a facet class need not have a public copy
|
|
// constructor, assignment, default constructor, destructor, etc.
|
|
|
|
// this, of course, makes the assumption that a default
|
|
// ctor is available
|
|
_Facet *__facet = new _Facet ();
|
|
|
|
__facet->_C_set_ref (__ref);
|
|
|
|
return __facet;
|
|
}
|
|
|
|
// -----------------------------------------------------
|
|
// Implementation helper class -- __rw_use_c_lib_locale.
|
|
// -----------------------------------------------------
|
|
|
|
class _RWSTD_EXPORT __rw_use_c_lib_locale
|
|
{
|
|
int _C_saved_cat;
|
|
char *_C_previous_locale_name;
|
|
public:
|
|
__rw_use_c_lib_locale (const char* = 0, int = LC_ALL);
|
|
|
|
~__rw_use_c_lib_locale ();
|
|
|
|
operator bool () const {
|
|
return _C_previous_locale_name != NULL;
|
|
}
|
|
};
|
|
|
|
|
|
// ---------------------------------------
|
|
// Inline members of __rw_use_c_lib_locale
|
|
// ---------------------------------------
|
|
|
|
// Destructor restores the C library locale that was in effect when the object
|
|
// was constructed.
|
|
inline __rw_use_c_lib_locale::~__rw_use_c_lib_locale ()
|
|
{
|
|
if (_C_previous_locale_name) {
|
|
setlocale(_C_saved_cat, _C_previous_locale_name);
|
|
|
|
delete[] _C_previous_locale_name;
|
|
}
|
|
}
|
|
|
|
|
|
template <class _Facet>
|
|
inline _Facet*
|
|
__rw_create_native_facet (_Facet*)
|
|
{
|
|
return __rw_create_named_facet ((_Facet*)0, "", _RWSTD_C::size_t (1));
|
|
}
|
|
|
|
|
|
_RWSTD_NAMESPACE_END // __rw
|
|
|
|
|
|
// functions below are defined here as a hack to allow explicit instantiation
|
|
// with automatic template instantiation (and implicit file inclusion); needed
|
|
// to guarantee that definitions of all instantiated entities have been seen
|
|
|
|
|
|
_RWSTD_NAMESPACE_BEGIN (std)
|
|
|
|
// Template use_facet<>() returns a reference to a facet. Its result is
|
|
// guaranteed by locale's value semantics to last at least as long as the
|
|
// locale or any copy of the locale it came from.
|
|
|
|
#ifndef _RWSTD_NO_TEMPLATE_ON_RETURN_TYPE
|
|
# define _RWSTD_SELECT_FACET(ignore)
|
|
#else
|
|
# define _RWSTD_SELECT_FACET(type) , type*
|
|
#endif
|
|
|
|
|
|
#ifndef _RWSTD_INLINE_INSTANTIATION_HACK
|
|
|
|
template <class _Facet>
|
|
inline const _Facet&
|
|
use_facet (const locale &__loc _RWSTD_SELECT_FACET (_Facet))
|
|
{
|
|
const _Facet &__facet = _RWSTD_STATIC_CAST (const _Facet&,
|
|
__loc._C_use_facet (_Facet::id,
|
|
_Facet::_C_ok_implicit,
|
|
_Facet::_C_facet_cat,
|
|
_RW::__rw_facet_maker<_Facet>::_C_maker_func));
|
|
|
|
return __facet;
|
|
}
|
|
|
|
#endif // _RWSTD_INLINE_INSTANTIATION_HACK
|
|
|
|
|
|
template <class _Facet>
|
|
inline bool
|
|
has_facet (const locale &__loc _RWSTD_SELECT_FACET (_Facet)) _THROWS (())
|
|
{
|
|
return _Facet::_C_ok_implicit || __loc._C_get_facet (_Facet::id);
|
|
}
|
|
|
|
|
|
#undef _RWSTD_SELECT_FACET
|
|
|
|
|
|
_RWSTD_NAMESPACE_END // std
|
|
|
|
|
|
#endif // _RWSTD_LOCALE_H_INCLUDED
|
|
|