Add basic_cpp_entity_ref generalization

This commit is contained in:
Jonathan Müller 2017-01-21 13:40:13 +01:00
commit 69f78d6abf
5 changed files with 71 additions and 64 deletions

View file

@ -0,0 +1,52 @@
// Copyright (C) 2017 Jonathan Müller <jonathanmueller.dev@gmail.com>
// This file is subject to the license terms in the LICENSE file
// found in the top-level directory of this distribution.
#ifndef CPPAST_CPP_ENTITY_REF_HPP_INCLUDED
#define CPPAST_CPP_ENTITY_REF_HPP_INCLUDED
#include <cppast/cpp_entity_index.hpp>
#include <cppast/cpp_entity_type.hpp>
namespace cppast
{
/// A basic reference to some kind of [cppast::cpp_entity]().
template <typename T, cpp_entity_type Type>
class basic_cpp_entity_ref
{
public:
/// \effects Creates it giving it the target id and name.
/// \requires An entity of matching type must eventually register in the [cppast::cpp_entity_index]() using that id.
basic_cpp_entity_ref(cpp_entity_id target_id, std::string target_name)
: target_(std::move(target_id)), name_(std::move(target_name))
{
}
/// \returns The name of the reference, as spelled in the source code.
const std::string& name() const noexcept
{
return name_;
}
/// \returns The [cppast::cpp_entity_id]() of the entity it refers to.
const cpp_entity_id& id() const noexcept
{
return target_;
}
/// \returns The [cppast::cpp_entity]() it refers to.
const T& get(const cpp_entity_index& idx) const noexcept
{
return detail::downcast_entity<const T&>(idx.lookup(target_).value(), Type);
}
private:
cpp_entity_id target_;
std::string name_;
};
/// A [cppast::basic_cpp_entity_ref]() to any [cppast::cpp_entity]().
using cpp_entity_ref = basic_cpp_entity_ref<cpp_entity, cpp_entity_type::count>;
} // namespace cppast
#endif // CPPAST_CPP_ENTITY_REF_HPP_INCLUDED

View file

@ -17,6 +17,8 @@ namespace cppast
namespace_t,
namespace_alias_t,
using_directive_t,
count,
};
/// \returns Whether or not a given entity type is one derived from [cppast::cpp_scope]().
@ -28,8 +30,8 @@ namespace cppast
template <typename T, typename Org>
T downcast_entity(Org& org, cpp_entity_type dest_type) noexcept
{
DEBUG_ASSERT(org.type() == dest_type, detail::precondition_error_handler{},
"invalid downcast");
DEBUG_ASSERT(dest_type == cpp_entity_type::count || org.type() == dest_type,
detail::precondition_error_handler{}, "invalid downcast");
return static_cast<T>(org);
}
} // namespace detail

View file

@ -6,6 +6,7 @@
#define CPPAST_CPP_NAMESPACE_HPP_INCLUDED
#include <cppast/cpp_entity_index.hpp>
#include <cppast/cpp_entity_ref.hpp>
#include <cppast/cpp_scope.hpp>
namespace cppast
@ -56,41 +57,16 @@ namespace cppast
{
}
cpp_entity_type do_get_entity_type() const noexcept override;
cpp_entity_type do_get_entity_type() const noexcept override
{
return cpp_entity_type::namespace_t;
}
bool inline_;
};
/// A reference to a [cppast::cpp_namespace]().
class cpp_namespace_ref
{
public:
/// \effects Creates it giving it the target id and name.
/// \requires A [cppast::cpp_namespace]() must register in the [cppast::cpp_entity_index]() with that id.
cpp_namespace_ref(cpp_entity_id target_id, std::string target_name)
: target_(std::move(target_id)), name_(std::move(target_name))
{
}
/// \returns The name of the reference, as spelled in the source code.
const std::string& name() const noexcept
{
return name_;
}
/// \returns The [cppast::cpp_entity_id]() of the namespace it refers to.
const cpp_entity_id& id() const noexcept
{
return target_;
}
/// \returns The [cppast::cpp_namespace]() it refers to.
const cpp_namespace& get(const cpp_entity_index& idx) const noexcept;
private:
cpp_entity_id target_;
std::string name_;
};
using cpp_namespace_ref = basic_cpp_entity_ref<cpp_namespace, cpp_entity_type::namespace_t>;
/// A [cppast::cpp_entity]() modelling a namespace alias.
class cpp_namespace_alias final : public cpp_entity
@ -119,7 +95,10 @@ namespace cppast
{
}
cpp_entity_type do_get_entity_type() const noexcept override;
cpp_entity_type do_get_entity_type() const noexcept override
{
return cpp_entity_type::namespace_alias_t;
}
cpp_namespace_ref target_;
};
@ -151,7 +130,10 @@ namespace cppast
{
}
cpp_entity_type do_get_entity_type() const noexcept override;
cpp_entity_type do_get_entity_type() const noexcept override
{
return cpp_entity_type::using_directive_t;
}
cpp_entity_id target_;
};

View file

@ -16,6 +16,7 @@ bool cppast::is_scope(cpp_entity_type type) noexcept
case cpp_entity_type::file_t:
case cpp_entity_type::namespace_alias_t:
case cpp_entity_type::using_directive_t:
case cpp_entity_type::count:
break;
}

View file

@ -1,30 +0,0 @@
// Copyright (C) 2017 Jonathan Müller <jonathanmueller.dev@gmail.com>
// This file is subject to the license terms in the LICENSE file
// found in the top-level directory of this distribution.
#include <cppast/cpp_namespace.hpp>
#include <cppast/cpp_entity_type.hpp>
using namespace cppast;
cpp_entity_type cpp_namespace::do_get_entity_type() const noexcept
{
return cpp_entity_type::namespace_t;
}
const cpp_namespace& cpp_namespace_ref::get(const cpp_entity_index& idx) const noexcept
{
return detail::downcast_entity<const cpp_namespace&>(idx.lookup(target_).value(),
cpp_entity_type::namespace_t);
}
cpp_entity_type cpp_namespace_alias::do_get_entity_type() const noexcept
{
return cpp_entity_type::namespace_alias_t;
}
cpp_entity_type cpp_using_directive::do_get_entity_type() const noexcept
{
return cpp_entity_type::using_directive_t;
}