`
zhangyafei_kimi
  • 浏览: 266153 次
  • 性别: Icon_minigender_1
  • 来自: 武汉
社区版块
存档分类
最新评论

boost.any源码整理和使用说明

 
阅读更多

Source

#include <algorithm>

#include <typeinfo>

#include "boost/config.hpp"

#include <boost/type_traits/remove_reference.hpp>

#include <boost/type_traits/is_reference.hpp>

#include <boost/throw_exception.hpp>

#include <boost/static_assert.hpp>

namespace kimi_boost

{

class any

{

template<typename ValueType>

friend ValueType * any_cast(any *);

public:

//ctor

any() : content(0){}

//ctor: from a value of any type

template<typename ValueType>

any(const ValueType & value): content(new holder<ValueType>(value)){}

//copy-ctor: from another any object

any(const any & other): content(other.content ? other.content->clone() : 0){}

//dtor

~any(){delete content;}

//swap two any objects

any& swap(any & rhs)

{

std::swap(content, rhs.content);

return *this;

}

//assign from a value of any type

template<typename ValueType>

any & operator=(const ValueType & rhs)

{

any(rhs).swap(*this);

return *this;

}

//assign from another any object

any & operator=(const any & rhs)

{

any(rhs).swap(*this);

return *this;

}

bool empty() const {return !content;}

//get the type_info& using RTTI

const std::type_info & type() const

{

//see holder::type()

return content ? content->type() : typeid(void);

}

private:

//inner class

class placeholder

{

public:

virtual ~placeholder(){}

virtual const std::type_info & type() const = 0;

virtual placeholder * clone() const = 0;

};//class placeholder

template<typename ValueType>

class holder : public placeholder

{

public:

holder(const ValueType & value): held(value){}

virtual const std::type_info & type() const

{return typeid(ValueType);}

//note the return type is "placeholder*" rather than "holder*"

virtual placeholder * clone() const

{return new holder(held);}

//the real object of various type

ValueType held;

};//class holder

private://the only member data

placeholder* content;

};//class any

//an exception class that will be thrown when type cast fails

class bad_any_cast : public std::bad_cast

{

public:

virtual const char * what() const throw()

{return "boost::bad_any_cast: failed conversion using boost::any_cast";}

};

//两个指针版本的any_cast不会抛出异常,失败时返回

//any_cast functions are based on typeid and type_info

template<typename ValueType>

ValueType * any_cast(any * operand)

{

return ( operand && operand->type() == typeid(ValueType) )

? &static_cast<any::holder<ValueType> *>(operand->content)->held

: 0;

}

template<typename ValueType>

const ValueType * any_cast(const any * operand)

{

return any_cast<ValueType>(const_cast<any *>(operand));

}

//两个引用版本的any_cast失败时会抛出异常

template<typename ValueType>

ValueType any_cast(const any & operand)

{

typedef typename remove_reference<ValueType>::type nonref;

const nonref * result = any_cast<nonref>(&operand);

if(!result)

boost::throw_exception(bad_any_cast());

return *result;

}

template<typename ValueType>

ValueType any_cast(any & operand)

{

typedef typename remove_reference<ValueType>::type nonref;

nonref * result = any_cast<nonref>(&operand);

if(!result)

boost::throw_exception(bad_any_cast());

return *result;

}

}

Test code

bool is_empty(const kimi_boost::any & operand)

{

return operand.empty();

}

bool is_int(const kimi_boost::any & operand)

{

return operand.type() == typeid(int);

}

bool is_char_ptr(const kimi_boost::any & operand)

{

try

{

kimi_boost::any_cast<const char *>(operand);

return true;

}

catch(const kimi_boost::bad_any_cast &)

{

return false;

}

}

bool is_string(const kimi_boost::any & operand)

{

return kimi_boost::any_cast<std::string>(&operand);

}

void count_all(std::list<kimi_boost::any> & values, std::ostream & out)

{

out << "#empty == "

<< std::count_if(values.begin(), values.end(), is_empty) << std::endl;

out << "#int == "

<< std::count_if(values.begin(), values.end(), is_int) << std::endl;

out << "#const char * == "

<< std::count_if(values.begin(), values.end(), is_char_ptr) << std::endl;

out << "#string == "

<< std::count_if(values.begin(), values.end(), is_string) << std::endl;

}

void any_test()

{

std::list<kimi_boost::any> la;

la.push_back(int(1));

la.push_back(double(1));

la.push_back(char(1));

la.push_back(float(1));

la.push_back(kimi_boost::any((char)3));//char type

la.push_back(kimi_boost::any((int)3));//int type

la.push_back(kimi_boost::any());//empty

la.push_back(kimi_boost::any());//empty

count_all(la,std::cout);

}

Output

#empty == 2

#int == 2

#const char * == 0

#string == 0

分享到:
评论

相关推荐

    Boost库学习指南与使用说明

    ### Boost库学习指南与使用说明 #### 一、Boost库简介 Boost库是一个高质量的、开源的C++库集合,提供了丰富的工具和组件,旨在帮助开发者编写高效、可移植的C++程序。Boost库不仅在C++社区内享有极高的声誉,而且...

    Boost库学习指南.pdf

    - **具体组件文档**:例如Boost.Assign、Boost.Regex和Boost.Array等组件的文档,详细介绍了各个组件的功能和使用方法。 - **源码分析**:对Boost库的部分源码进行了深度解析,帮助高级用户理解其内部实现机制。 ##...

    muduo-master.zip_BOOST服务器_muduo

    muduo利用了Boost的许多特性,如Boost.Thread用于线程管理和同步,Boost.Any用于存储任意类型的对象,以及Boost.Function和Boost.Bind实现函数对象和函数绑定等。 在“muduo-master”文件夹中,除了muduo的源代码外...

    c++资源Boost库及指南

    - **开源免费**:Boost库完全开源,用户可以自由地使用、修改和分发。 - **可移植性强**:可以在多种操作系统和编译器环境下使用。 - **标准化进程的推动者**:许多Boost库的功能最终被采纳进入C++标准库。 - **社区...

    BOOST学习指南

    此外,Boost库中包含的代码是完全开放源代码的,用户可以在遵循Boost许可证的前提下自由使用和修改。 Boost库包含了大量的库组件,这些组件覆盖了从智能指针到线程编程等多个方面。其中,智能指针是管理动态分配...

    boost1.57源代码

    boost当前最新1.57版本源代码包。 Updated Libraries: Any, Asio, Circular Buffer, Config, Container, Coroutine, Flyweight, Geometry, Interprocess, Intrusive, Iterator, Lexical Cast, Math, Move, ...

    Loki库源码(泛型模式C++库)

    Loki is not tied to thebook anymore as it already has a lot of new components (e.g. -StrongPtr, Printf, and Scopeguard). Loki inspired similar tools andfunctionality now also present in the [1][2]...

    C++反射&&可用于搭建通用框架

    在C++中,我们可以使用如Boost库中的Boost.TypeErasure或者使用C++17引入的std::any、std::function等工具来实现一定程度的反射效果。此外,还有一些社区开发的库,如RTTR(Runtime Type Reflection)提供更完善的...

    Visual C++ 编程资源大全(英文源码 DLL)

    05.zip Getting the complete information about DLL/Exe module 得到DLL/EXE模块的编译信息(5KB)&lt;END&gt;&lt;br&gt;6,06.zip Using one extension DLL in another 在DLL中使用扩充的DLL(4KB)&lt;END&gt;&lt;br&gt;7,...

    c++ winsock编程

    在标签"源码"和"工具"中,源码可能指的是示例代码或完整项目,工具可能指的是用于辅助开发的库或框架,例如Boost.Asio,它可以简化C++的网络编程工作,提供了更高级别的抽象。 在提供的压缩包文件“5-7”中,可能...

    dlib库的whl文件大全-适配pyhon3.6-3.10各个版本的

    它包含了已编译的扩展模块和其他资源,使得开发者可以在不进行源码编译的情况下安装包,尤其适用于没有C编译器或者编译环境复杂的场景。Python的`pip`工具可以直接处理whl文件,通过命令`pip install package_name....

    C++中typeid实现原理详解

    最近看了boost::any类源码,其实现主要依赖typeid操作符。很好奇这样实现的时间和空间开销有多大,决定探一下究竟。 VS2008附带的type_info类只有头文件,没有源文件,声明如下: class type_info { public: ...

Global site tag (gtag.js) - Google Analytics