Used boost::variant in Union-like classes.

This commit is contained in:
Kirill Kirilenko 2017-02-16 00:49:39 +03:00
parent ea28b547eb
commit 014411a8a3
2 changed files with 24 additions and 97 deletions

View file

@ -4,6 +4,8 @@
#include <string> #include <string>
#include <vector> #include <vector>
#include <boost/variant/variant.hpp>
#define TELEBOTXX_DECLARE_BOOL_PARAM_CLASS(Name, DEFAULT) class Name \ #define TELEBOTXX_DECLARE_BOOL_PARAM_CLASS(Name, DEFAULT) class Name \
{ \ { \
public: \ public: \
@ -39,11 +41,7 @@ public:
const std::string getUsername() const; const std::string getUsername() const;
private: private:
Type type_; Type type_;
union boost::variant<int, std::string> value_;
{
int id_;
std::string username_;
};
}; };
TELEBOTXX_DECLARE_STRING_PARAM_CLASS(Text); TELEBOTXX_DECLARE_STRING_PARAM_CLASS(Text);
@ -108,13 +106,7 @@ public:
private: private:
Type type_; Type type_;
union boost::variant<int, Buffer, File, Url> value_;
{
int id_;
Buffer buffer_;
File file_;
Url url_;
};
}; };
} }

View file

@ -1,5 +1,7 @@
#include <telebotxx/RequestOptions.hpp> #include <telebotxx/RequestOptions.hpp>
#include <boost/variant.hpp>
#define TELEBOTXX_DEFINE_BOOL_PARAM_CLASS(Name) Name::Name(bool value) : value_(value) { } \ #define TELEBOTXX_DEFINE_BOOL_PARAM_CLASS(Name) Name::Name(bool value) : value_(value) { } \
bool Name::getValue() const { return value_; } bool Name::getValue() const { return value_; }
@ -9,44 +11,18 @@ const std::string& Name::getValue() const { return value_; }
namespace telebotxx { namespace telebotxx {
ChatId::ChatId(int id) ChatId::ChatId(int id)
: type_(Type::Id), id_(id) : type_(Type::Id), value_(id)
{ {
} }
ChatId::ChatId(const std::string& str) ChatId::ChatId(const std::string& str)
: type_(Type::Username), username_(str) : type_(Type::Username), value_(str)
{ {
} }
ChatId::ChatId(const ChatId& other) ChatId::ChatId(const ChatId& other) = default;
: type_(other.type_) ChatId::ChatId(ChatId&& other) = default;
{ ChatId::~ChatId() = default;
if (type_ == Type::Id)
id_ = other.id_;
else
new(&username_) std::string(other.username_);
}
ChatId::ChatId(ChatId&& other)
: type_(std::move(other.type_))
{
if (type_ == Type::Id)
{
id_ = other.id_;
other.id_ = 0;
}
else
{
new(&username_) std::string(std::move(other.username_));
other.username_.~basic_string();
}
}
ChatId::~ChatId()
{
if (type_ == Type::Username)
username_.~basic_string();
}
ChatId::Type ChatId::getType() const ChatId::Type ChatId::getType() const
{ {
@ -55,12 +31,12 @@ ChatId::Type ChatId::getType() const
const int ChatId::getId() const const int ChatId::getId() const
{ {
return id_; return boost::get<int>(value_);
} }
const std::string ChatId::getUsername() const const std::string ChatId::getUsername() const
{ {
return username_; return boost::get<std::string>(value_);
} }
//////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////
@ -129,69 +105,28 @@ TELEBOTXX_DEFINE_STRING_PARAM_CLASS(Url)
//////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////
Photo::Photo(int id) Photo::Photo(int id)
: type_(Type::Id), id_(id) : type_(Type::Id), value_(id)
{ {
} }
Photo::Photo(const Buffer& buffer) Photo::Photo(const Buffer& buffer)
: type_(Type::Buffer), buffer_(buffer) : type_(Type::Buffer), value_(buffer)
{ {
} }
Photo::Photo(const File& file) Photo::Photo(const File& file)
: type_(Type::File), file_(file) : type_(Type::File), value_(file)
{ {
} }
Photo::Photo(const Url& url) Photo::Photo(const Url& url)
: type_(Type::Url), url_(url) : type_(Type::Url), value_(url)
{ {
} }
Photo::Photo(const Photo& other) Photo::Photo(const Photo& other) = default;
: type_(other.type_) Photo::Photo(Photo&& other) = default;
{ Photo::~Photo() = default;
if (type_ == Type::Id)
id_ = other.id_;
else if (type_ == Type::Buffer)
new(&buffer_) Buffer(other.buffer_);
else if (type_ == Type::File)
new(&file_) File(other.file_);
else
new(&url_) Url(other.url_);
}
Photo::Photo(Photo&& other)
{
if (type_ == Type::Id)
{
id_ = other.id_;
other.id_ = 0;
}
else if (type_ == Type::Buffer)
{
new(&buffer_) Buffer(std::move(other.buffer_));
other.buffer_.~Buffer();
}
else if (type_ == Type::File)
{
new(&file_) File(std::move(other.file_));
other.file_.~File();
}
else
{
new(&url_) Url(std::move(other.url_));
other.url_.~Url();
}
}
Photo::~Photo()
{
if (type_ == Type::File)
file_.~File();
else if (type_ == Type::Url)
url_.~Url();
}
Photo::Type Photo::getType() const Photo::Type Photo::getType() const
{ {
@ -200,22 +135,22 @@ Photo::Type Photo::getType() const
int Photo::getId() const int Photo::getId() const
{ {
return id_; return boost::get<int>(value_);
} }
const Buffer& Photo::getBuffer() const const Buffer& Photo::getBuffer() const
{ {
return buffer_; return boost::get<Buffer>(value_);
} }
const File& Photo::getFile() const const File& Photo::getFile() const
{ {
return file_; return boost::get<File>(value_);
} }
const Url& Photo::getUrl() const const Url& Photo::getUrl() const
{ {
return url_; return boost::get<Url>(value_);
} }
} }