首页 » C/C++ » C/C++程序设计

C/C++基础

类型转换(Type Casting)

隐式转换,如将long变量赋值给int变量等(可能导致精度损失),此为语言内建的标准转换。C++语言有其他方法支持隐式转换:

class A {};
class B {
    public:
        B(const A& a) { printf("construct B from A\n"); }
        operator int() const { return 0; }
};

int main()
{
    A a;
    B b = a;            // output: construct B from A
    int x = b;
    printf("%d\n", x);  // output: 0

    return 0;
}

C++中有一个关键字explicit来规避类构造函数引起的隐式转换:

显示转换,有如(float)i这样的C风格,或float(i)这样的新风格。C++引入了4中类型转换操作符:

类型转换 说明
static_cast<type>(expression) 类似旧式类型转换。
dynamic_cast<type>(expression) 继承体系中安全向下类型转换。
const_cast<type>(expression) 去除对象的const属性
reinterpret_cast<type>(expression) 低级类型转换,不常见

C++模版技术

模版特化

模版特化分为全特化(complete specialization)和偏特化(partcial specialization)。在声明时,一定要把最普通的模版写在最前面,特化的模版写在后面:

template<typename T> class Vector;                // 普通的模版类
template<typename T> class Vector<T*>;      // 特化,针对指针
template<> class Vector<int*>;              // 特化,针对整形指针

下面是一段简单的测试代码:

// genernal
template<typename T>
class Vector
{
    public:
        Vector() { printf("template<typename T> class Vector\n"); };
};

// partcial specialization
template<typename T>
class Vector<T*>
{
    public:
        Vector() { printf("template<typename T> class Vector<T*>\n"); }
};

// complete specialization
template<>
class Vector<int*>
{
     public:
        Vector() { printf("template<> class Vector<int*>\n"); }
};

int main()
{
    Vector<int> vi;
    Vector<char*> vcp;
    Vector<int*> vip;
    Vector<int**> vipp;   // template<typename T> class Vector<T*>

    return 0;
}

C++异常处理

C++异常处理由3个关键字构成:throw, try, catch,它的语法结构如下:

try {
    throw exception();
}
catch(exception) {
    /* ... */
}

构造和析构函数中的异常

构造函数没有返回值,要检查是否构造成功,就需要依赖一些状态值的设置,但用异常似乎更好:

FilePtr::FilePtr(const char* filename, const char* mode)
{
    if((p == fopen(filename, mode)) == 0) {
        throw open_file_failed();
    }
}

构造函数使用异常要注意的是:如果对象只被部分构造,则析构函数不能被正常调用。例如:

Buffer::Buffer(int len) {
    _buf = new char[len];
    init();     // throw exception
}
Buffer::~Buffer() {
    delete[] _buf;
}

如果init()抛出异常,Buffer对象没有完成构造,就造成内存泄漏。

分享

0

评论

comments powered by Disqus