正文

Concepts and Rvalue Reference : C++0x wi2007-01-09 00:26:00

【评论】 【打印】 【字体: 】 本文链接:http://blog.pfan.cn/sonicling/22388.html

分享到:

Concepts and Rvalue Reference : C++0x will come C++0x马上就要出来了。目前已经有许多提议已经大致成型,下面是最有可能出现在C++0x标准中的几个提议: 一、Concepts Concept是BS极力要加入的一个新特性,用来对模板实例进行限制。例如 template<typename T>T max(T a, T b){    return a<b?b:a;} typename关键字允许T是任何实例,但是max的代码却对T有隐含的限制:T必须能够用“<”进行比较。 再例如 template<typename InputIterator>InputIterator advance(InputIterator iter, size_t n){    //...} InputIterator必须能够进行++操作。而考虑到advance对不同iterator的优化,可能需要iter+n的操作。 为了让编译器有效检查泛型参数的实例类型,加入Concept特性。 声明一个Concept: auto concept LessThanCompareable<typename T>{    bool operator < (T, T); // 必须存在该函数}; auto关键字表示对运算符重载进行更广义的匹配,例如T::operator(const T&)也被认为符合上面的Concept template<LessThanCompareable T>T max(T a, T b){    return a<b?b:a;} 或者使用where从句 template<typename T>T max(T a, T b)where LessThanCompareable<T>{    return a<b?b:a;} where从句可以对多个参数进行联合检查:auto concept Convertible<typename U, typename S>{    operator U (S);}; template<typename U, typename S>U conv(S src)where Convertible<U, S>{   return src;} 对于Iterator,可以定义如下概念: auto concept IteratorInterface<typename Iter>{   // 标准迭代器的5个关联类型    typename value_type;    typename reference;    typename pointer;    typename difference_type;    typename iterator_category;    // 相关标准操作    reference operator*(const Iter&); // 解引用}; concept  MemberCheck<typename T>{    T::T(); // 存在默认构造    T::T(const T&); //存在拷贝构造    T::~T(); // 存在析构    T::operator = (const T&); // 存在赋值运算符}; auto concept  InputIterator<typename Iter>{    where MemberCheck<Iter>    where IteratorInterface<Iter>    // 或者where MemberCheck<Iter> && IteratorInterface<Iter>    Iter& operator++(Iter&);    Iter operator++(Iter&, int);}; concept  ForwardIterator<typename Iter> : InputIterator<Iter>{}; auto concept  BidirectionalIterator<typename Iter> : ForwardIterator<Iter>{    Iter& operator--(Iter&);    Iter operator--(Iter&, int);}; auto concept  RandomAccessIterator<typename Iter> : BidirectionalIterator<Iter>{    Iter& operator+(Iter&, int);    Iter& operator-(Iter&, int);}; iterator_category其实已经可以不需要了。 还可以使用concept_map对类型进行关联映射: concept_map InputIterator<char*> {    typedef char value_type;    typedef char& reference;    typedef char* pointer;    typedef std::ptrdiff_t difference type;    //..}; 这样,指针就自动拥有标准迭代器所具有的所有关联类型,iterator_traits可以寿终正寝了。 二、Rvalue Reference C++的引用属于lvalue const reference,它与Java的引用不同: C++:Object obj1, obj2;Object& robj = obj1; // robj=>obj1robj = obj2; // robj.operator=(obj2); robj=>obj1 ! Java:Object obj1 = new Object();Object obj2 = new Object();Object robj = obj1; // robj=>obj1robj = obj2; // robj=>obj2 ! C++的lvalue const reference不能引用non-const rvalue: int &r = 10; // 错int a = 10;int &r = a; // ok, r=>aint b = 11;r = b; // a = b, r=>a, b被解释为lvalue而非non-const rvalue void func(int &); //#1void func(const int &); //#2func(10); // #2 const rvaluefunc(*new int(10)); // #1 lvalue C++0x将引入新的引用类型:Rvalue Reference: int &&rr = 0; // rr=>0 non-const rvalue ref可以引用const rvalueint a = 10;rr = a; // rr=>rvalue(a)=10int b = 11;int &r = b; // r=>brr = r; // rr=>rvalue(r)=rvalue(b)=11, a=10(没有改变) Object &&rr = Object(); // 允许引用临时对象Object &r = Object(); // 错误。 两种引用的组合的标准转换: A& & = A&    A的引用的引用转换为引用A& && = A&   A的引用的rvalue引用转换为引用A&& & = A&   A的rvalue引用的引用转换为引用A&& && = A&& A的rvalue引用的rvalue引用转换为rvalue引用 rvalue reference导致新增加两种重要的成员函数:移动构造和移动赋值 class string{private:    char * p;public:    string(const string &str) // 拷贝构造 copy-constructor    {        p = new char[strlen(str.p)+1];        strcpy(p, str.p);    }    string& operator = (const string &str) // 拷贝赋值 copy-assignment    {        p = new char[strlen(str.p)+1];        strcpy(p, str.p);        return *this;    }    string(string &&str) // 移动构造 move-constructor    {        p = str.p;    }    string& operator = (string &&str) // 移动赋值 move-assignment    {        p = str.p;        return *this;    }}; 为什么string(const string &str)不能直接将str.p赋值给p?因为str具有const属性,无法将const var赋值给non-const var。为什么不将string(const string &str)写为string(string &str),operator=(const string &str)写为operator=(string &str)?因为后者不接受临时对象等rvalue表达式为参数,(string &&str)接受non-const rvalue,因此无法用(string &str)代替(string &&str)。 对于下面的交换算法: void swap(string &a, string &b){    string t = a;    a = b;    b = t;} 根据目前标准只能使用拷贝构造和拷贝赋值来编译。到了C++0x,由于增加了移动构造和移动赋值,因此效率可以大大提高!(注:a和b为lvalue,根据目前标准,可以转换为rvalue。See ISO/IEC 14882 4.1 Lvalue-to-rvalue conversion) 三、其他改进 list<vector<int>> 中“>>”可以被正确接受 增加auto声明。下面的代码for(std::vector<my_element_type>::iterator it=v.begin(); it!=v.end(); ++it)可以写为for(auto it=v.begin(); it!=v.end(); ++it)auto声明的变量,其类型可以由编译器通过初始值判断得出。 增加Delegating Constructors特性:class object{public:    object() : _i(0), _d(0.0) {}    object(int i) : _i(i), _d(0.0) {}    object(double d) : _i(0), _d(d) {}    object(int i, double d) : _i(i), _d(d) {}};其初始化列表写起来繁琐而容易出错。新特性允许如下初始化:class object{public:    object() : object(0, 0.0) {} // 用object(int,double)初始化    object(int i) : object(i, 0.0) {} // 用object(int,double)初始化    object(double d) : object(0, d) {} // 用object(int,double)初始化    object(int i, double d) : _i(i), _d(d) {}}; 还增加了诸如weak_ptr等特性。以上特性是最后可能加入新标准的几个,拿出来给大家看看。

阅读(3940) | 评论(0)


版权声明:编程爱好者网站为此博客服务提供商,如本文牵涉到版权问题,编程爱好者网站不承担相关责任,如有版权问题请直接与本文作者联系解决。谢谢!

评论

暂无评论
您需要登录后才能评论,请 登录 或者 注册