<iostream>
namespace std {
extern istream cin;
extern ostream cout;
extern ostream cerr;
extern ostream clog;
extern wistream wcin;
extern wostream wcout;
extern wostream wcerr;
extern wostream wclog;
};
cin是什么?
cin
extern istream cin;
The object controls extractions from the standard input as a byte stream. Once the object is constructed, the call cin.tie() returns &cout.
cout是什么?
cout
extern ostream cout;
The object controls insertions to the standard output as a byte stream.
/@@/ 帮助文档
ios_base::fmtflags
typedef T1 fmtflags;
static const fmtflags boolalpha, dec, fixed, hex, internal,
left, oct, right, scientific, showbase, showpoint,
showpos, skipws, unitbuf, uppercase, adjustfield,
basefield, floatfield;
The type is an enumerated type T1 that describes an object that can store format flags. The distinct flag values are:
boolalpha, to insert or extract objects of type bool as names (such as true and false) rather than as numeric values.
dec, to insert or extract integer values in decimal format.
fixed, to insert floating-point values in fixed-point format (with no exponent field).
hex, to insert or extract integer values in hexadecimal format.
internal, to pad to a field width as needed by inserting fill characters at a point internal to a generated numeric field.
left, to pad to a field width as needed by inserting fill characters at the end of a generated field (left justification).
oct, to insert or extract integer values in octal format.
right, to pad to a field width as needed by inserting fill characters at the beginning of a generated field (right justification).
scientific, to insert floating-point values in scientific format (with an exponent field).
showbase, to insert a prefix that reveals the base of a generated integer field.
showpoint, to insert a decimal point unconditionally in a generated floating-point field.
showpos, to insert a plus sign in a non-negative generated numeric field.
skipws, to skip leading white space before certain extractions.
unitbuf, to flush output after each insertion.
uppercase, to insert uppercase equivalents of lowercase letters in certain insertions.
In addition, several useful values are:
adjustfield, internal | left | right
basefield, dec | hex | oct
floatfield, fixed | scientific
format flags | values |
---|---|
adjustfield | internal left right |
basefield | dec hex oct |
floatfield | fixed scientific |
/*
The class describes the storage and member functions common to both
input and output streams that do not depend on the template parameters.
(The template class basic_ios describes what is common and is dependent on template parameters.)
*/
// 查考@@帮助文档,帮助理解ios_base类
class ios_base {
public:
class failure;
typedef T1 fmtflags;
static const fmtflags boolalpha, dec, fixed, hex, internal,
left, oct, right, scientific, showbase, showpoint,
showpos, skipws, unitbuf, uppercase, adjustfield,
basefield, floatfield;
typedef T2 iostate;
static const iostate badbit, eofbit, failbit, goodbit;
typedef T3 openmode;
static const openmode app, ate, binary, in, out, trunc;
typedef T4 seekdir;
static const seekdir beg, cur, end;
typedef T5 event;
static const event copyfmt_event, erase_event,
copyfmt_event;
class Init;
ios_base& operator=(const ios_base& rhs);
fmtflags flags() const;
fmtflags flags(fmtflags fmtfl);
fmtflags setf(fmtflags fmtfl);
fmtflags setf(fmtflags fmtfl, fmtflags mask);
void unsetf(fmtflags mask);
streamsize precision() const;
streamsize precision(streamsize prec);
streamsize width() const;
stramsize width(streamsize wide);
locale imbue(const locale& loc);
locale getloc() const;
static int xalloc();
long& iword(int idx);
void *& pword(int idx);
typedef void *(event_callback(event ev, ios_base& ios, int idx);
void register_callback(event_callback pfn, int idx);
static bool sync_with_stdio(bool sync = true);
protected:
ios_base();
};
/*
The template class describes the storage and member functions common to
both input streams (of template class basic_istream) and output streams
(of template class basic_ostream) that depend on the template parameters.
*/
template <class E, class T = char_traits<E> >
class basic_ios : public ios_base {
public:
typedef E char_type;
typedef T::int_type int_type;
typedef T::pos_type pos_type;
typedef T::off_type off_type;
explicit basic_ios(basic_streambuf<E, T>* sb);
virtual ~basic_ios();
operator void *() const;
bool operator!() const;
iostate rdstate() const;
void clear(iostate state = goodbit);
void setstate(iostate state);
bool good() const;
bool eof() const;
bool fail() const;
bool bad() const;
iostate exceptions() const;
iostate exceptions(iostate except);
basic_ios& copyfmt(const basic_ios& rhs);
E fill() const;
E fill(E ch);
basic_ostream<E, T> *tie() const;
basic_ostream<E, T> *tie(basic_ostream<E, T> *str);
basic_streambuf<E, T> *rdbuf() const;
basic_streambuf<E, T> *rdbuf(basic_streambuf<E, T> *sb);
basic_ios& copyfmt(const basic_ios& rhs);
locale imbue(const locale& loc);
E widen(char ch);
char narrow(E ch, char dflt);
protected:
basic_ios();
void init(basic_streambuf<E, T>* sb);
};
/*
The template class describes an object that controls extraction of elements and encoded objects from a stream buffer with elements of type E, whose character traits are determined by the class T.
*/
template <class E, class T = char_traits<E> >
class basic_istream : virtual public basic_ios<E, T> {
public:
class sentry;
explicit basic_istream(basic_streambuf<E, T> *sb);
virtual ~istream();
bool ipfx(bool noskip = false);
void isfx();
basic_istream& operator>>(basic_istream& (*pf)(basic_istream&));
basic_istream& operator>>(basic_ios<E, T>& (*pf)(basic_ios<E, T>&));
basic_istream& operator>>(ios_base<E, T>& (*pf)(ios_base<E, T>&));
basic_istream& operator>>(basic_streambuf<E, T> *sb);
basic_istream& operator>>(bool& n);
basic_istream& operator>>(short& n);
basic_istream& operator>>(unsigned short& n);
basic_istream& operator>>(int& n);
basic_istream& operator>>(unsigned int& n);
basic_istream& operator>>(long& n);
basic_istream& operator>>(unsigned long& n);
basic_istream& operator>>(void *& n);
basic_istream& operator>>(float& n);
basic_istream& operator>>(double& n);
basic_istream& operator>>(long double& n);
streamsize gcount() const;
int_type get();
basic_istream& get(E& c);
basic_istream& get(E *s, streamsize n);
basic_istream& get(E *s, streamsize n, E delim);
basic_istream& get(basic_streambuf<E, T> *sb);
basic_istream& get(baiic_streambuf<E, T> *sb, E delim);
basic_istream& getline(E *s, streamsize n)E
basic_istream& getline(E *s, streamsize n, E delim);
basic_istream& ignore(streamsize n = 1,
int_type delim = T::eof());
int_type peek();
basic_istream& read(E *s, streamsize n);
streamsize readsome(E *s, streamsize n);
basic_istream& putback(E c);
basic_istream& unget();
pos_type tellg();
basic_istream& seekg(pos_type pos);
basic_istream& seekg(off_type off, ios_base::seek_dir way);
int sync();
};
/*
The template class describes an object that controls extraction of elements and encoded objects from a stream buffer of class basic_filebuf<E, T>, with elements of type E, whose character traits are determined by the class T. The object stores an object of class basic_filebuf<E, T>.
*/
template <class E, class T = char_traits<E> >
class basic_ifstream : public basic_istream<E, T> {
public:
explicit basic_ifstream();
explicit basic_ifstream(const char *s,
ios_base::openmode mode = ios_base::in);
basic_filebuf<E, T> *rdbuf() const;
bool is_open() const;
void open(const char *s,
ios_base::openmode mode = ios_base::in);
void close();
};
/*
The template class describes an object that controls extraction of elements and encoded objects from a stream buffer of class basic_stringbuf<E, T, A>, with elements of type E, whose character traits are determined by the class T, and whose elements are allocated by an allocator of class A. The object stores an object of class basic_stringbuf<E, T, A>.
*/
template <class E,
class T = char_traits<E>,
class A = allocator<E> >
class basic_istringstream : public basic_istream<E, T> {
public:
explicit basic_istringstream(ios_base::openmode mode = ios_base::in);
explicit basic_istringstream(const basic_string<E, T, A>& x,
ios_base::openmode mode = ios_base::in);
basic_stringbuf<E, T, A> *rdbuf() const;
basic_string<E, T, A>& str();
void str(const basic_string<E, T, A>& x);
};
/*
The template class describes an object that controls insertion of elements and encoded objects into a stream buffer with elements of type E, whose character traits are determined by the class T.
*/
template <class E, class T = char_traits<E> >
class basic_ostream : virtual public basic_ios<E, T>{
public:
class sentry;
explicit basic_ostream(basic_streambuf<E, T> *sb);
virtual ~ostream();
bool opfx();
void osfx();
basic_ostream& operator<<(basic_ostream& (*pf)(basic_ostream&));
basic_ostream& operator<<(basic_ios<E, T>& (*pf)(basic_ios<E, T>&));
basic_ostream& operator<<(ios_base<E, T>& (*pf)(ios_base<E, T>&));
basic_ostream& operator<<(basic_streambuf<E, T> *sb);
basic_ostream& operator<<(const char *s);
basic_ostream& operator<<(char c);
basic_ostream& operator<<(bool n);
basic_ostream& operator<<(short n);
basic_ostream& operator<<(unsigned short n);
basic_ostream& operator<<(int n);
basic_ostream& operator<<(unsigned int n);
basic_ostream& operator<<(long n);
basic_ostream& operator<<(unsigned long n);
basic_ostream& operator<<(float n);
basic_ostream& operator<<(double n);
basic_ostream& operator<<(long double n);
basic_ostream& operator<<(void * n);
basic_ostream& put(E c);
basic_ostream& write(E *s, streamsize n);
basic_ostream& flush();
pos_type tellp();
basic_ostream& seekp(pos_type pos);
basic_ostream& seekp(off_type off, ios_base::seek_dir way);
};
/*
The template class describes an object that controls insertion of elements and encoded objects into a stream buffer of class basic_stringbuf<E, T, A>, with elements of type E, whose character traits are determined by the class T, and whose elements are allocated by an allocator of class A. The object stores an object of class basic_stringbuf<E, T, A>.
*/
template <class E,
class T = char_traits<E>,
class A = allocator<E> >
class basic_ostringstream : public basic_ostream<E, T> {
public:
explicit basic_ostringstream(ios_base::openmode mode = ios_base::out);
explicit basic_ostringstream(const basic_string<E, T, A>& x,
ios_base::openmode mode = ios_base::out);
basic_stringbuf<E, T, A> *rdbuf() const;
basic_string<E, T, A>& str();
void str(const basic_string<E, T, A>& x);
};
/*
The template class describes an object that controls insertion of elements and encoded objects into a stream buffer of class basic_filebuf<E, T>, with elements of type E, whose character traits are determined by the class T. The object stores an object of class basic_filebuf<E, T>.
*/
template <class E, class T = char_traits<E> >
class basic_ofstream : public basic_ostream<E, T> {
public:
explicit basic_ofstream();
explicit basic_ofstream(const char *s,
ios_base::openmode mode = ios_base::out | ios_base::trunc);
basic_filebuf<E, T> *rdbuf() const;
bool is_open() const;
void open(const char *s,
ios_base::openmode mode = ios_base::out | ios_base::trunc);
void close();
};
/*
The template class describes an object that controls insertions,
through its base object basic_ostream<E, T>, and extractions,
through its base object basic_istream<E, T>. The two objects
share a common virtual base object basic_ios<E, T>.
They also manage a common stream buffer, with elements of type E,
whose character traits are determined by the class T.
The constructor initializes its base objects via basic_istream(sb) and basic_ostream(sb).
*/
template <class E, class T = char_traits<E> >
class basic_iostream : public basic_istream<E, T>,
public basic_ostream<E, T> {
public:
explicit basic_iostream(basic_streambuf<E, T> *sb);
virtual ~basic_iostream();
};
/*
The template class describes an object that controls insertion and
extraction of elements and encoded objects using a stream
buffer of class basic_stringbuf<E, T, A>, with elements of type E,
whose character traits are determined by the class T,
and whose elements are allocated by an allocator of class A.
The object stores an object of class basic_stringbuf<E, T, A>.
*/
template <class E,
class T = char_traits<E>,
class A = allocator<E> >
class basic_stringstream : public basic_iostream<E, T> {
public:
explicit basic_stringstream(ios_base::openmode mode = ios_base::in | ios_base::out);
explicit basic_stringstream(const basic_string<E, T, A>& x,
ios_base::openmode mode = ios_base::in | ios_base::out);
basic_stringbuf<E, T, A> *rdbuf() const;
basic_string<E, T, A>& str();
void str(const basic_string<E, T, A>& x);
};
template <class E, class T = char_traits<E> >
class basic_streambuf {
public:
typedef E char_type;
typedef T traits_type;
typedef T::int_type int_type;
typedef T::pos_type pos_type;
typedef T::off_type off_type;
virtual ~streambuf();
locale pubimbue(const locale& loc);
locale getloc() const;
basic_streambuf *pubsetbuf(E *s, streamsize n);
pos_type pubseekoff(off_type off, ios_base::seekdir way,
ios_base::openmode which = ios_base::in | ios_base::out);
pos_type pubseekpos(pos_type sp,
ios_base::openmode which = ios_base::in | ios_base::out);
int pubsync();
streamsize in_avail();
int_type snextc();
int_type sbumpc();
int_type sgetc();
streamsize sgetn(E *s, streamsize n);
int_type sputbackc(E c);
int_type sungetc();
int_type sputc(E c);
streamsize sputn(const E *s, streamsize n);
protected:
basic_streambuf();
E *eback() const;
E *gptr() const;
E *egptr() const;
void gbump(int n);
void setg(E *gbeg, E *gnext, E *gend);
E *pbase() const;
E *pptr() const;
E *epptr() const;
void pbump(int n);
void setp(E *pbeg, E *pend);
virtual void imbue(const locale &loc);
virtual basic_streambuf *setbuf(E *s, streamsize n);
virtual pos_type seekoff(off_type off, ios_base::seekdir way,
ios_base::openmode which = ios_base::in | ios_base::out);
virtual pos_type seekpos(pos_type sp,
ios_base::openmode which = ios_base::in | ios_base::out);
virtual int sync();
virtual int showmanyc();
virtual streamsize xsgetn(E *s, streamsize n);
virtual int_type underflow();
virtual int_type uflow();
virtual int_type pbackfail(int_type c = T::eof());
virtual streamsize xsputn(const E *s, streamsize n);
virtual int_type overflow(int_type c = T::eof());
};
template <class E, class T = char_traits<E> >
class basic_filebuf : public basic_streambuf<E, T> {
public:
basic_filebuf();
bool is_open() const;
basic_filebuf *open(const char *s, ios_base::openmode mode);
basic_filebuf *close();
protected:
virtual pos_type seekoff(off_type off, ios_base::seekdir way,
ios_base::openmode which = ios_base::in | ios_base::out);
virtual pos_type seekpos(pos_type pos,
ios_base::openmode which = ios_base::in | ios_base::out);
virtual int_type underflow();
virtual int_type pbackfail(int_type c = T::eof());
virtual int_type overflow(int_type c = T::eof());
virtual int sync();
virtual basic_streambuf<E, T> *setbuf(E *s, streamsize n);
};
template <class E,
class T = char_traits<E>,
class A = allocator<E> >
class basic_stringbuf {
public:
basic_stringbuf(ios_base::openmode mode =
ios_base::in | ios_base::out);
basic_stringbuf(basic_string<E, T, A>& x,
ios_base::openmode mode = ios_base::in | ios_base::out);
basic_string<E, T, A> str() const;
void str(basic_string<E, T, A>& x);
protected:
virtual pos_type seekoff(off_type off, ios_base::seekdir way,
ios_base::openmode mode = ios_base::in | ios_base::out);
virtual pos_type seekpos(pos_type sp,
ios_base::openmode mode = ios_base::in | ios_base::out);
virtual int_type underflow();
virtual int_type pbackfail(int_type c = T::eof());
virtual int_type overflow(int_type c = T::eof());
};
template<class E,
class T = char_traits<E>,
class A = allocator<T> >
class basic_string {
public:
typedef T traits_type;
typedef A allocator_type;
typedef T::char_type char_type;
typedef A::size_type size_type;
typedef A::difference_type difference_type;
typedef A::pointer pointer;
typedef A::const_pointer const_pointer;
typedef A::reference reference;
typedef A::const_reference const_reference;
typedef A::value_type value_type;
typedef T0 iterator;
typedef T1 const_iterator;
typedef reverse_iterator<iterator, value_type,
reference, pointer, difference_type>
reverse_iterator;
typedef reverse_iterator<const_iterator, value_type,
const_reference, const_pointer, difference_type>
const_reverse_iterator;
static const size_type npos = -1;
explicit basic_string(const A& al = A());
basic_string(const basic_string& rhs);
basic_string(const basic_string& rhs, size_type pos, size_type n,
const A& al = A());
basic_string(const E *s, size_type n, const A& al = A());
basic_string(const E *s, const A& al = A());
basic_string(size_type n, E c, const A& al = A());
basic_string(const_iterator first, const_iterator last,
const A& al = A());
basic_string& operator=(const basic_string& rhs);
basic_string& operator=(const E *s);
basic_string& operator=(E c);
iterator begin();
const_iterator begin() const;
iterator end();
const_iterator end() const;
reverse_iterator rbegin();
const_reverse_iterator rbegin() const;
reverse_iterator rend();
const_reverse_iterator rend() const;
const_reference at(size_type pos) const;
reference at(size_type pos);
const_reference operator[](size_type pos) const;
reference operator[](size_type pos);
const E *c_str() const;
const E *data() const;
size_type length() const;
size_type size() const;
size_type max_size() const;
void resize(size_type n, E c = E());
size_type capacity() const;
void reserve(size_type n = 0);
bool empty() const;
basic_string& operator+=(const basic_string& rhs);
basic_string& operator+=(const E *s);
basic_string& operator+=(E c);
basic_string& append(const basic_string& str);
basic_string& append(const basic_string& str,
size_type pos, size_type n);
basic_string& append(const E *s, size_type n);
basic_string& append(const E *s);
basic_string& append(size_type n, E c);
basic_string& append(const_iterator first, const_iterator last);
basic_string& assign(const basic_string& str);
basic_string& assign(const basic_string& str,
size_type pos, size_type n);
basic_string& assign(const E *s, size_type n);
basic_string& assign(const E *s);
basic_string& assign(size_type n, E c);
basic_string& assign(const_iterator first, const_iterator last);
basic_string& insert(size_type p0,
const basic_string& str);
basic_string& insert(size_type p0,
const basic_string& str, size_type pos, size_type n);
basic_string& insert(size_type p0,
const E *s, size_type n);
basic_string& insert(size_type p0, const E *s);
basic_string& insert(size_type p0, size_type n, E c);
iterator insert(iterator it, E c);
void insert(iterator it, size_type n, E c);
void insert(iterator it,
const_iterator first, const_iterator last);
basic_string& erase(size_type p0 = 0, size_type n = npos);
iterator erase(iterator it);
iterator erase(iterator first, iterator last);
basic_string& replace(size_type p0, size_type n0,
const basic_string& str);
basic_string& replace(size_type p0, size_type n0,
const basic_string& str, size_type pos, size_type n);
basic_string& replace(size_type p0, size_type n0,
const E *s, size_type n);
basic_string& replace(size_type p0, size_type n0,
const E *s);
basic_string& replace(size_type p0, size_type n0,
size_type n, E c);
basic_string& replace(iterator first0, iterator last0,
const basic_string& str);
basic_string& replace(iterator first0, iterator last0,
const E *s, size_type n);
basic_string& replace(iterator first0, iterator last0,
const E *s);
basic_string& replace(iterator first0, iterator last0,
size_type n, E c);
basic_string& replace(iterator first0, iterator last0,
const_iterator first, const_iterator last);
size_type copy(E *s, size_type n, size_type pos = 0) const;
void swap(basic_string& str);
size_type find(const basic_string& str,
size_type pos = 0) const;
size_type find(const E *s, size_type pos, size_type n) const;
size_type find(const E *s, size_type pos = 0) const;
size_type find(E c, size_type pos = 0) const;
size_type rfind(const basic_string& str,
size_type pos = npos) const;
size_type rfind(const E *s, size_type pos,
size_type n = npos) const;
size_type rfind(const E *s, size_type pos = npos) const;
size_type rfind(E c, size_type pos = npos) const;
size_type find_first_of(const basic_string& str,
size_type pos = 0) const;
size_type find_first_of(const E *s, size_type pos,
size_type n) const;
size_type find_first_of(const E *s, size_type pos = 0) const;
size_type find_first_of(E c, size_type pos = 0) const;
size_type find_last_of(const basic_string& str,
size_type pos = npos) const;
size_type find_last_of(const E *s, size_type pos,
size_type n = npos) con/t;
size_type find_last_of(const E *s, size_type pos = npos) const;
size_type find_last_of(E c, size_type pos = npos) const;
size_type find_first_not_of(const basic_string& str,
size_type pos = 0) const;
size_type find_first_not_of(const E *s, size_type pos,
size_type n) const;
size_type find_first_not_of(const E *s, size_type pos = 0) const;
size_type find_first_not_of(E c, size_type pos = 0) const;
size_type find_last_not_of(const basic_string& str,
size_type pos = npos) const;
size_type find_last_not_of(const E *s, size_type pos,
size_type n) const;
size_type find_last_not_of(const E *s,
size_type pos = npos) const;
size_type find_last_not_of(E c, size_type pos = npos) const;
basic_string substr(size_type pos = 0, size_type n = npos) const;
int compare(const basic_string& str) const;
int compare(size_type p0, size_type n0,
const basic_string& str);
int compare(size_type p0, size_type n0,
const basic_string& str, size_type pos, size_type n);
int compare(const E *s) const;
int compare(size_type p0, size_type n0,
const E *s) const;
int compare(size_type p0, size_type n0,
const E *s, size_type pos) const;
A get_allocator() const;
protected:
A allocator;
};
char_traits是什么?
至于上次这个问号,是从std::string的使用中发现的
typedef basic_string string;
而
template<class E,class traits = char_traits,
class Alloc = allocator >
class basic_string;
所以就对 char_traits 产生了问好?
以后有机会了再来研究 allocator
/// 21.1.3.1 char_traits specializations
template <class char_type, class _Int_type>
struct _Char_traits { // properties of a string or stream element
{
typedef char char_type;
typedef int int_type;
typedef streampos pos_type;
typedef streamoff off_type;
typedef mbstate_t state_type;
static _GLIBCXX17_CONSTEXPR void
assign(char_type& __c1, const char_type& __c2) _GLIBCXX_NOEXCEPT
{ __c1 = __c2; }
static _GLIBCXX_CONSTEXPR bool
eq(const char_type& __c1, const char_type& __c2) _GLIBCXX_NOEXCEPT
{ return __c1 == __c2; }
static _GLIBCXX_CONSTEXPR bool
lt(const char_type& __c1, const char_type& __c2) _GLIBCXX_NOEXCEPT
{
// LWG 467.
return (static_cast<unsigned char>(__c1)
< static_cast<unsigned char>(__c2));
}
static /* _GLIBCXX17_CONSTEXPR */ int
compare(const char_type* __s1, const char_type* __s2, size_t __n)
{
if (__n == 0)
return 0;
return __builtin_memcmp(__s1, __s2, __n);
}
static /* _GLIBCXX17_CONSTEXPR */ size_t
length(const char_type* __s)
{ return __builtin_strlen(__s); }
static /* _GLIBCXX17_CONSTEXPR */ const char_type*
find(const char_type* __s, size_t __n, const char_type& __a)
{
if (__n == 0)
return 0;
return static_cast<const char_type*>(__builtin_memchr(__s, __a, __n));
}
static char_type*
move(char_type* __s1, const char_type* __s2, size_t __n)
{
if (__n == 0)
return __s1;
return static_cast<char_type*>(__builtin_memmove(__s1, __s2, __n));
}
static char_type*
copy(char_type* __s1, const char_type* __s2, size_t __n)
{
if (__n == 0)
return __s1;
return static_cast<char_type*>(__builtin_memcpy(__s1, __s2, __n));
}
static char_type*
assign(char_type* __s, size_t __n, char_type __a)
{
if (__n == 0)
return __s;
return static_cast<char_type*>(__builtin_memset(__s, __a, __n));
}
static _GLIBCXX_CONSTEXPR char_type
to_char_type(const int_type& __c) _GLIBCXX_NOEXCEPT
{ return static_cast<char_type>(__c); }
// To keep both the byte 0xff and the eof symbol 0xffffffff
// from ending up as 0xffffffff.
static _GLIBCXX_CONSTEXPR int_type
to_int_type(const char_type& __c) _GLIBCXX_NOEXCEPT
{ return static_cast<int_type>(static_cast<unsigned char>(__c)); }
static _GLIBCXX_CONSTEXPR bool
eq_int_type(const int_type& __c1, const int_type& __c2) _GLIBCXX_NOEXCEPT
{ return __c1 == __c2; }
static _GLIBCXX_CONSTEXPR int_type
eof() _GLIBCXX_NOEXCEPT
{ return static_cast<int_type>(_GLIBCXX_STDIO_EOF); }
static _GLIBCXX_CONSTEXPR int_type
not_eof(const int_type& __c) _GLIBCXX_NOEXCEPT
{ return (__c == eof()) ? 0 : __c; }
};
template <class _Ty>
class allocator {
public:
static_assert(!is_const_v<_Ty>, "The C++ Standard forbids containers of const elements "
"because allocator<const T> is ill-formed.");
using _From_primary = allocator;
using value_type = _Ty;
typedef _Ty* pointer;
typedef const _Ty* const_pointer;
typedef _Ty& reference;
typedef const _Ty& const_reference;
using size_type = size_t;
using difference_type = ptrdiff_t;
using propagate_on_container_move_assignment = true_type;
using is_always_equal = true_type;
template <class _Other>
struct rebind {
using other = allocator<_Other>;
};
_NODISCARD _Ty* address(_Ty& _Val) const noexcept {
return _STD addressof(_Val);
}
_NODISCARD const _Ty* address(const _Ty& _Val) const noexcept {
return _STD addressof(_Val);
}
constexpr allocator() noexcept {}
constexpr allocator(const allocator&) noexcept = default;
template <class _Other>
constexpr allocator(const allocator<_Other>&) noexcept {}
void deallocate(_Ty* const _Ptr, const size_t _Count) {
// no overflow check on the following multiply; we assume _Allocate did that check
_Deallocate<_New_alignof<_Ty>>(_Ptr, sizeof(_Ty) * _Count);
}
_NODISCARD __declspec(allocator) _Ty* allocate(_CRT_GUARDOVERFLOW const size_t _Count) {
return static_cast<_Ty*>(_Allocate<_New_alignof<_Ty>>(_Get_size_of_n<sizeof(_Ty)>(_Count)));
}
_NODISCARD __declspec(allocator) _Ty* allocate(
_CRT_GUARDOVERFLOW const size_t _Count, const void*) {
return allocate(_Count);
}
template <class _Objty, class... _Types>
void construct(_Objty* const _Ptr, _Types&&... _Args) {
::new (const_cast<void*>(static_cast<const volatile void*>(_Ptr))) _Objty(_STD forward<_Types>(_Args)...);
}
template <class _Uty>
void destroy(_Uty* const _Ptr) {
_Ptr->~_Uty();
}
_NODISCARD size_t max_size() const noexcept {
return static_cast<size_t>(-1) / sizeof(_Ty);
}
};
除了使用继承将父类的特性和功能加到用户类中,还可以通过组合其他类到
用户类中扩展功能,但是其实还有一种方法来给一个用户类扩充功能,那就
是通过模板实现,如下,自己细品。
using string = basic_string<char,char_traits<char>,allocator<char> >
template<class _Elem,char _Traits = char_traits<_Elem>,class _Alloc = allocator<_Elem> >
class basic_string{
// basic_string也即std::string中比较,相等,小于,复制,赋值,移动,长度,获取类型等操作来源于
// 模板参数中的第二个char_traits<char>提供
}
会查资料的能力很重要
知道权威的官方资料文档如何查询
https://learn.microsoft.com/zh-cn/cpp/standard-library/char-traits-struct?view=msvc-170