typeinfo类型支持库学习

type_info是保有一个类型的实现指定信息的类,这里的类型不仅包括类,结构体,数值类型比如,int,double,还包括对象,指针。通过typeid运算符返回的类,可以获取该类型的指定信息包括类型的名称和比较二个类型相等的方法或相对顺序,hash_code等。

成员函数

(析构函数)

[虚]

虚析构函数使 type_info 为多态类
(虚公开成员函数)

operator==operator!=

(C++20 中移除)

检查对象是否指代相同类型
(公开成员函数)

before

检查在实现定义的顺序中,被指代类型是否在另一个 type_info 对象之前,即对被指代类型排序
(公开成员函数)

hash_code

(C++11)

返回对于同一类型相同的值
(公开成员函数)

name

类型的实现定义名称
(公开成员函数)

下面是具体的示例

#include <iostream>
#include <string>
#include <typeinfo>
#include <utility>

using namespace std;

class Person {
public:
    Person(string name):
        m_name(std::move(name))
    {

    }

    virtual const string& name() const
    {
        return m_name;
    }

private:
    string m_name;
};

class Employee: public Person {
public:
    Employee(string name, string per):
        Person(std::move(name)),
        m_profession(std::move(per))
    {

    }

    const string &profession() const
    {
        return m_profession;
    }

private:
    string m_profession;
};

void somefunc(const Person& per)
{
    if(typeid(Person) == typeid(per))
    {
        cout << per.name() << " is not an employee \n";
    }
    else if(typeid (Employee) == typeid(per))
    {
        cout << per.name() << " is an Employee ";
        auto &emp = dynamic_cast<const Employee&>(per);
        cout << "who works in " << emp.profession() << "\n";
    }
}

//结构体
struct SBase {
public:
    virtual ~SBase() = default;
};

struct SDerived: SBase {

};

//类
class CBase {
public:
    virtual ~CBase() = default;
};

class CDerived: public CBase {

};

int main()
{
    //1.1获取对象的类型信息
    SBase sbase;
    SDerived sderived;
    const SBase *pb = &sbase;
    cout << "sbase=== name = " << typeid(sbase).name() << " raw_name = " << typeid(sbase).raw_name() << " hash_code = " << typeid(sbase).hash_code() << endl;
    cout << "pb===    name = " << typeid(pb).name() << " raw_name = " << typeid(pb).raw_name() << " hash_code = " << typeid(pb).hash_code() << endl;
    cout << "*pb===   name = " << typeid(*pb).name() << " raw_name = " << typeid(*pb).raw_name() << " hash_code = " << typeid(*pb).hash_code() << endl;
    pb = &sderived;
    cout << "*pb===   name = " << typeid(*pb).name() << " raw_name = " << typeid(*pb).raw_name() << " hash_code = " << typeid(*pb).hash_code() << endl;

    CBase cbase;
    CDerived cderived;
    const CBase *pbc = &cbase;
    cout << "*pbc===  name = " << typeid(*pbc).name() << " raw_name = " << typeid(*pbc).raw_name() << " hash_code = " << typeid(*pbc).hash_code() << endl;
    pbc = &cderived;
    cout << "*pbc==   name = " << typeid(*pbc).name() << " raw_name = " << typeid(*pbc).raw_name() << " hash_code = " << typeid(*pbc).hash_code() << endl;

    //1.2 获取普通变量的类型信息
    int n = 30;
    const type_info &info = typeid(n);
    cout << "int===   name = " << info.name() << " raw_name = " << info.raw_name() << " hash_code = " << info.hash_code() << endl;

    //1.3 获取一个字面量的类型信息
    const type_info &literalInfo = typeid(19.6);
    cout << "19.6==   name = " << literalInfo.name() << " raw_name = " << literalInfo.raw_name() << " hash_code = " << literalInfo.hash_code() << endl;

    //1.4 获取表达式的类型信息
    const type_info &expressionInfo = typeid(50 / 2 * 3.6);
    cout << "expression name = " << expressionInfo.name() << " raw_name = " << expressionInfo.raw_name() << " hash_code = " << expressionInfo.hash_code() << endl;
    //1.5 获取结构体的类型信息
    const type_info &sinfo = typeid(SBase);
    cout << "SBase   name = " << sinfo.name() << " raw_name = " << sinfo.raw_name() << " hash_code = " << sinfo.hash_code() << endl;
    //1.6 获取类的类型信息
    const type_info &cinfo = typeid(CBase);
    cout << "CBase   name = " << cinfo.name() << " raw_name = " << cinfo.raw_name() << " hash_code = " << cinfo.hash_code() << endl;

    //2. operator==的使用
    somefunc(Employee{"Scott", "Camel"});
    somefunc(Person{"Yak"});

    //3. operator!=的使用
    if (typeid(Employee) != typeid(Person))
    {
        cout << "class 'Employee' != class 'Person' \n";
    }

    cout << endl;
    //4.before
    if(typeid(char).before(typeid(bool)))
        std::cout << "char goes before bool in this implementation.\n";
    else
        std::cout << "bool goes before char in this implementation.\n";

    if(typeid(char).before(typeid(short)))
        std::cout << "char goes before short in this implementation.\n";
    else
        std::cout << "short goes before char in this implementation.\n";


    if(typeid(int).before(typeid(char)))
        std::cout << "int goes before char in this implementation.\n";
    else
        std::cout << "char goes before int in this implementation.\n";


    cout << "Hello World!" << endl;
    return 0;
}

运行结果:

接下来看一下hash_code()函数的使用:

#include <iostream>
#include <typeinfo>
#include <unordered_map>
#include <string>
#include <functional>
#include <memory>

using namespace std;

struct A {
    virtual ~A() {}
};

struct B : A {};
struct C : A {};

using TypeInfoRef = std::reference_wrapper<const std::type_info>;

struct Hasher {
    std::size_t operator()(TypeInfoRef code) const
    {
        return code.get().hash_code();
    }
};

struct EqualTo {
    bool operator()(TypeInfoRef lhs, TypeInfoRef rhs) const
    {
        return lhs.get() == rhs.get();
    }
};

int main()
{
    std::unordered_map<TypeInfoRef, std::string, Hasher, EqualTo> type_names;

    type_names[typeid(int)] = "int";
    type_names[typeid(double)] = "double";
    type_names[typeid(A)] = "A";
    type_names[typeid(B)] = "B";
    type_names[typeid(C)] = "C";

    int i;
    double d;
    A a;

    // note that we're storing pointer to type A
    std::unique_ptr<A> b(new B);
    std::unique_ptr<A> c(new C);

    std::cout << "i is " << type_names[typeid(i)] << '\n';
    std::cout << "d is " << type_names[typeid(d)] << '\n';
    std::cout << "a is " << type_names[typeid(a)] << '\n';
    std::cout << "b is " << type_names[typeid(*b)] << '\n';
    std::cout << "c is " << type_names[typeid(*c)] << '\n';
    cout << "Hello World!" << endl;
    return 0;
}

运行结果:

参考:

<typeinfo> - C++ Reference

标准库头文件 <typeinfo> - cppreference.com

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值