#ifndef NODE_IMPL_H_62B23520_7C8E_11DE_8A39_0800200C9A66 #define NODE_IMPL_H_62B23520_7C8E_11DE_8A39_0800200C9A66 #if defined(_MSC_VER) || (defined(__GNUC__) && (__GNUC__ == 3 && __GNUC_MINOR__ >= 4) || (__GNUC__ >= 4)) // GCC supports "pragma once" correctly since 3.4 #pragma once #endif #include "yaml-cpp/node/node.h" #include "yaml-cpp/node/iterator.h" #include "yaml-cpp/node/detail/memory.h" #include "yaml-cpp/node/detail/node.h" #include namespace YAML { inline Node::Node(): m_pNode(0) { } inline Node::Node(NodeType::value type): m_pMemory(new detail::memory_holder), m_pNode(&m_pMemory->create_node()) { m_pNode->set_type(type); } template inline Node::Node(const T& rhs): m_pMemory(new detail::memory_holder), m_pNode(&m_pMemory->create_node()) { Assign(rhs); } inline Node::Node(const Node& rhs): m_pMemory(rhs.m_pMemory), m_pNode(rhs.m_pNode) { } inline Node::Node(detail::node& node, detail::shared_memory_holder pMemory): m_pMemory(pMemory), m_pNode(&node) { } inline Node::~Node() { } inline void Node::EnsureNodeExists() const { if(!m_pNode) { m_pMemory.reset(new detail::memory_holder); m_pNode = &m_pMemory->create_node(); m_pNode->set_null(); } } inline NodeType::value Node::Type() const { return m_pNode ? m_pNode->type() : NodeType::Null; } // access template inline const T Node::as() const { if(!m_pNode) throw std::runtime_error("Unable to convert to type"); T t; if(convert::decode(*this, t)) return t; throw std::runtime_error("Unable to convert to type"); } template<> inline const std::string Node::as() const { if(Type() != NodeType::Scalar) throw std::runtime_error("Unable to convert to string, not a scalar"); return Scalar(); } inline const std::string& Node::Scalar() const { return m_pNode ? m_pNode->scalar() : detail::node_data::empty_scalar; } inline const std::string& Node::Tag() const { return m_pNode ? m_pNode->tag() : detail::node_data::empty_scalar; } inline void Node::SetTag(const std::string& tag) { EnsureNodeExists(); m_pNode->set_tag(tag); } // assignment inline bool Node::is(const Node& rhs) const { return m_pNode ? m_pNode->is(*rhs.m_pNode) : false; } template inline Node& Node::operator=(const T& rhs) { Assign(rhs); return *this; } template inline void Node::Assign(const T& rhs) { AssignData(convert::encode(rhs)); } template<> inline void Node::Assign(const std::string& rhs) { EnsureNodeExists(); m_pNode->set_scalar(rhs); } inline void Node::Assign(const char *rhs) { EnsureNodeExists(); m_pNode->set_scalar(rhs); } inline void Node::Assign(char *rhs) { EnsureNodeExists(); m_pNode->set_scalar(rhs); } inline Node& Node::operator=(const Node& rhs) { if(is(rhs)) return *this; AssignNode(rhs); return *this; } inline void Node::AssignData(const Node& rhs) { EnsureNodeExists(); rhs.EnsureNodeExists(); m_pNode->set_data(*rhs.m_pNode); m_pMemory->merge(*rhs.m_pMemory); } inline void Node::AssignNode(const Node& rhs) { rhs.EnsureNodeExists(); if(!m_pNode) { m_pNode = rhs.m_pNode; m_pMemory = rhs.m_pMemory; return; } m_pNode->set_ref(*rhs.m_pNode); m_pMemory->merge(*rhs.m_pMemory); m_pNode = rhs.m_pNode; } // size/iterator inline std::size_t Node::size() const { return m_pNode ? m_pNode->size() : 0; } inline const_iterator Node::begin() const { return m_pNode ? const_iterator(m_pNode->begin(), m_pMemory) : const_iterator(); } inline iterator Node::begin() { return m_pNode ? iterator(m_pNode->begin(), m_pMemory) : iterator(); } inline const_iterator Node::end() const { return m_pNode ? const_iterator(m_pNode->end(), m_pMemory) : const_iterator(); } inline iterator Node::end() { return m_pNode ? iterator(m_pNode->end(), m_pMemory) : iterator(); } // sequence template inline void Node::append(const T& rhs) { append(Node(rhs)); } inline void Node::append(const Node& rhs) { EnsureNodeExists(); rhs.EnsureNodeExists(); m_pNode->append(*rhs.m_pNode, m_pMemory); m_pMemory->merge(*rhs.m_pMemory); } // indexing template inline const Node Node::operator[](const Key& key) const { EnsureNodeExists(); detail::node& value = static_cast(*m_pNode).get(key, m_pMemory); return Node(value, m_pMemory); } template inline Node Node::operator[](const Key& key) { EnsureNodeExists(); detail::node& value = m_pNode->get(key, m_pMemory); return Node(value, m_pMemory); } template inline bool Node::remove(const Key& key) { EnsureNodeExists(); return m_pNode->remove(key, m_pMemory); } inline const Node Node::operator[](const Node& key) const { EnsureNodeExists(); key.EnsureNodeExists(); detail::node& value = static_cast(*m_pNode).get(*key.m_pNode, m_pMemory); return Node(value, m_pMemory); } inline Node Node::operator[](const Node& key) { EnsureNodeExists(); key.EnsureNodeExists(); detail::node& value = m_pNode->get(*key.m_pNode, m_pMemory); return Node(value, m_pMemory); } inline bool Node::remove(const Node& key) { EnsureNodeExists(); key.EnsureNodeExists(); return m_pNode->remove(*key.m_pNode, m_pMemory); } inline const Node Node::operator[](const char *key) const { return operator[](std::string(key)); } inline Node Node::operator[](const char *key) { return operator[](std::string(key)); } inline bool Node::remove(const char *key) { return remove(std::string(key)); } inline const Node Node::operator[](char *key) const { return operator[](static_cast(key)); } inline Node Node::operator[](char *key) { return operator[](static_cast(key)); } inline bool Node::remove(char *key) { return remove(static_cast(key)); } // free functions inline bool operator==(const Node& lhs, const Node& rhs) { return lhs.is(rhs); } } #endif // NODE_IMPL_H_62B23520_7C8E_11DE_8A39_0800200C9A66