conversion function转换函数

class Fraction {
public:
    Fraction(int num, int den = 1)
    : m_numerator(num), m_denominator(den) { }
    //转换函数是没有前面的返回值,没有参数
    operator double() const {
        return (double) (m_numerator / m_denominator);
    }

private:
    int m_numerator;
    int m_denominator;
};

Fraction(3,5);
double d = 4 + f;
//编译器会以各种方式判断语句是否会通过,如果重载了「+」,则会优先查找该操作符,判断是否有一个参数为(整数,Fraction)的操作符重载
//上面的Fraction类定义了double()转换函数,执行语句时,会调用转换函数把f转换为double型,然后与4相加

//假设没有定义转换函数,而是重载了操作符+
    Fraction operator+(const Fraction& f) {
        return Fraction(...);
    }
template<class Alloc>
class vector<bool, Alloc> {
public:
    typedef __bit_reference reference;
protected:
    reference operator[] (size type n) {
        return *(begin() + difference_type(n));
    }
    ...
};

struct __bit_referencee referencee {
    unsigned int* p;
    unsigned int mask;
    ...
public:
    operator bool() const {
        return !(!(*p & mask))
    }
    ...
};

explicit

//two parameter, one argument, 称谓non-explicit-one-argument ctor
    Fraction(int num, int den=1)
    : m_numerator(num), m_denominator(den) { }

//假设还是调用如下的函数
Fraction(3,5);
double d = 4 + f;
//此时编译器可以找到这样的逻辑链条:将4转换为Fraction(只需要1个参数,所以能成功),然后再利用重载的+进行运算

如果是如下的情况

class Fraction {
public:
    Fraction(int num, int den = 1)
    : m_numerator(num), m_denominator(den) {
    }
    operator double() const {
        return (double) (m_numerator / m_denominator);
    }
    Fraction operator+(const Fraction& f) {
        return Fraction(...);
    }

private:
    int m_numerator;
    int m_denominator;
};

Fraction(3,5);
Fraction d2 = 4 + f;
//[Error]ambiguous

//如果指定了关键字
    explicit Fraction(int num, int den = 1)
    : m_numerator(num), m_denominator(den) {
    }

Fraction d2 = 4 + f;
//[Error]conversion from 'double' to 'Fraciton' requests denied
//此时4就不会自动的转化为Fraction type,于是乎就会调用重载的+进行运算,但由于参数不匹配报错

pointer-like classes, 智能指针

template<class T>
class shared_ptr {
public:
    T& operator*() const {
        return *px;
    }
    T& operator->() const {
        return px;
    }
    shared_ptr(T* p) : px(p) { }

private:
    T* px;
    long* pn;
    ...
};

关于迭代器

template<class T, class Ref, class Ptr>
struct __list_iterator {
    typedef __list_iterator<T, Ref, Ptr> self;
    typedef Ptr pointer;
    typedef Ref reference;
    typedef __list_node<T>* link_type;
    /*
    template <class T>
    struct __list_node {
        void* prev;
        void* next;
        T data;
    }
    */
    link_type node;
    bool operator==(const self& x) const;
    bool operator!(const self& x) const { return node != x.node; }
    reference operator*() const { return (*node).data; }
    pointer operator->() const {return &(operator*()); }
    self& operator++() { node = (link_type)((*node).next); return *this; }
    self& operator++(int) { self tmp = *this; ++*this; return tmp; }
    self& operator--() { node = (link_type)((*node).prev); return *this; }
    self& operator--(int) { self tmp = *this; --*this; return tmp; }
};

function like classes, 仿函数

template <class T>
struct identity : public unary_function <T,T>{
    const T&
    operator() (const T& x) const { return x;}
};
//某种意义上可以认为,仿函数就是将()这个特殊的操作符重载

namespace

编程时要牢记分开来,这样层次比较清晰

#include "iostream"
#include "random.h"

using namespace std;

#include <iostream>
#include <memory>

namespace hitomi01 {
    ...
}//namesapce 01

#include <iostream>
#include <list>
namespace hitomi02 {
    ...
}//namespace 02

member template, 成员模板

template <class T1, class T2>
struct pair {
    typedef T1 first_type;
    typedef T2 second_type;

    T1 first;
    T2 second;

    pair() : first(T1()), second(T2()) { }
    pair(const T1& a, const T2& b) : first(a), second(b) { }
    //成员模板
    template<class U1, class U2>
            pair(const pair<U1, U2>& p) : first(p.first), second(p.second) { }
};

specialzation, 模板特化