Skip to content

Commit

Permalink
Simplified the implementation of implicit casts
Browse files Browse the repository at this point in the history
  • Loading branch information
bblanchon committed Apr 8, 2020
1 parent 2097ffa commit ec43bf4
Show file tree
Hide file tree
Showing 8 changed files with 56 additions and 80 deletions.
5 changes: 5 additions & 0 deletions src/ArduinoJson/Array/ElementProxy.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,11 @@ class ElementProxy : public VariantOperators<ElementProxy<TArray> >,
return getUpstreamElement().template as<T>();
}

template <typename T>
FORCE_INLINE operator T() const {
return getUpstreamElement();
}

template <typename T>
FORCE_INLINE bool is() const {
return getUpstreamElement().template is<T>();
Expand Down
5 changes: 5 additions & 0 deletions src/ArduinoJson/Object/MemberProxy.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,11 @@ class MemberProxy : public VariantOperators<MemberProxy<TObject, TStringRef> >,
return getUpstreamMember().template as<TValue>();
}

template <typename T>
FORCE_INLINE operator T() const {
return getUpstreamMember();
}

template <typename TValue>
FORCE_INLINE bool is() const {
return getUpstreamMember().template is<TValue>();
Expand Down
24 changes: 0 additions & 24 deletions src/ArduinoJson/Operators/VariantCasts.hpp

This file was deleted.

4 changes: 1 addition & 3 deletions src/ArduinoJson/Operators/VariantOperators.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -4,16 +4,14 @@

#pragma once

#include <ArduinoJson/Operators/VariantCasts.hpp>
#include <ArduinoJson/Operators/VariantComparisons.hpp>
#include <ArduinoJson/Operators/VariantOr.hpp>
#include <ArduinoJson/Operators/VariantShortcuts.hpp>

namespace ARDUINOJSON_NAMESPACE {

template <typename TImpl>
class VariantOperators : public VariantCasts<TImpl>,
public VariantComparisons<TImpl>,
class VariantOperators : public VariantComparisons<TImpl>,
public VariantOr<TImpl>,
public VariantShortcuts<TImpl> {};
} // namespace ARDUINOJSON_NAMESPACE
32 changes: 20 additions & 12 deletions src/ArduinoJson/Variant/VariantAs.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -53,44 +53,52 @@ struct VariantConstAs<ArrayRef> {

template <typename T>
inline typename enable_if<is_integral<T>::value, T>::type variantAs(
const VariantData* _data) {
return _data != 0 ? _data->asIntegral<T>() : T(0);
const VariantData* data) {
return data != 0 ? data->asIntegral<T>() : T(0);
}

template <typename T>
inline typename enable_if<is_same<T, bool>::value, T>::type variantAs(
const VariantData* _data) {
return _data != 0 ? _data->asBoolean() : false;
const VariantData* data) {
return data != 0 ? data->asBoolean() : false;
}

template <typename T>
inline typename enable_if<is_floating_point<T>::value, T>::type variantAs(
const VariantData* _data) {
return _data != 0 ? _data->asFloat<T>() : T(0);
const VariantData* data) {
return data != 0 ? data->asFloat<T>() : T(0);
}

template <typename T>
inline typename enable_if<is_same<T, const char*>::value ||
is_same<T, char*>::value,
const char*>::type
variantAs(const VariantData* _data) {
return _data != 0 ? _data->asString() : 0;
variantAs(const VariantData* data) {
return data != 0 ? data->asString() : 0;
}

template <typename T>
T variantAs(VariantData* data, MemoryPool*) {
// By default use the read-only conversion.
// There are specializations for
// - ArrayRef
return variantAs<T>(data);
}

template <typename T>
inline typename enable_if<is_same<ArrayConstRef, T>::value, T>::type variantAs(
const VariantData* _data);
const VariantData* data);

template <typename T>
inline typename enable_if<is_same<ObjectConstRef, T>::value, T>::type variantAs(
const VariantData* _data);
const VariantData* data);

template <typename T>
inline typename enable_if<is_same<VariantConstRef, T>::value, T>::type
variantAs(const VariantData* _data);
variantAs(const VariantData* data);

template <typename T>
inline typename enable_if<IsWriteableString<T>::value, T>::type variantAs(
const VariantData* _data);
const VariantData* data);

} // namespace ARDUINOJSON_NAMESPACE
15 changes: 15 additions & 0 deletions src/ArduinoJson/Variant/VariantAsImpl.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -39,4 +39,19 @@ inline typename enable_if<IsWriteableString<T>::value, T>::type variantAs(
return s;
}

template <>
inline ArrayRef variantAs<ArrayRef>(VariantData* data, MemoryPool* pool) {
return ArrayRef(pool, data != 0 ? data->asArray() : 0);
}

template <>
inline ObjectRef variantAs<ObjectRef>(VariantData* data, MemoryPool* pool) {
return ObjectRef(pool, data != 0 ? data->asObject() : 0);
}

template <>
inline VariantRef variantAs<VariantRef>(VariantData* data, MemoryPool* pool) {
return VariantRef(pool, data);
}

} // namespace ARDUINOJSON_NAMESPACE
12 changes: 0 additions & 12 deletions src/ArduinoJson/Variant/VariantImpl.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -83,18 +83,6 @@ typename enable_if<IsVisitable<TVariant>::value, bool>::type VariantRef::set(
return variantCopyFrom(_data, v._data, _pool);
}

template <typename T>
inline typename enable_if<is_same<T, ArrayRef>::value, T>::type VariantRef::as()
const {
return ArrayRef(_pool, _data != 0 ? _data->asArray() : 0);
}

template <typename T>
inline typename enable_if<is_same<T, ObjectRef>::value, T>::type
VariantRef::as() const {
return ObjectRef(_pool, variantAsObject(_data));
}

template <typename T>
inline typename enable_if<is_same<T, ArrayRef>::value, ArrayRef>::type
VariantRef::to() const {
Expand Down
39 changes: 10 additions & 29 deletions src/ArduinoJson/Variant/VariantRef.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -246,36 +246,14 @@ class VariantRef : public VariantRefBase<VariantData>,
return variantSetSignedInteger(_data, static_cast<Integer>(value));
}

// Get the variant as the specified type.
//
// std::string as<std::string>() const;
// String as<String>() const;
template <typename T>
FORCE_INLINE typename enable_if<!is_same<T, ArrayRef>::value &&
!is_same<T, ObjectRef>::value &&
!is_same<T, VariantRef>::value,
typename VariantAs<T>::type>::type
as() const {
return variantAs<T>(_data);
FORCE_INLINE typename VariantAs<T>::type as() const {
return variantAs<typename VariantAs<T>::type>(_data, _pool);
}
//
// ArrayRef as<ArrayRef>() const;
// const ArrayRef as<const ArrayRef>() const;
template <typename T>
FORCE_INLINE typename enable_if<is_same<T, ArrayRef>::value, T>::type as()
const;
//
// ObjectRef as<ObjectRef>() const;
// const ObjectRef as<const ObjectRef>() const;
template <typename T>
FORCE_INLINE typename enable_if<is_same<T, ObjectRef>::value, T>::type as()
const;
//
// VariantRef as<VariantRef> const;

template <typename T>
FORCE_INLINE typename enable_if<is_same<T, VariantRef>::value, T>::type as()
const {
return *this;
FORCE_INLINE operator T() const {
return variantAs<T>(_data, _pool);
}

template <typename Visitor>
Expand Down Expand Up @@ -376,13 +354,16 @@ class VariantConstRef : public VariantRefBase<const VariantData>,
variantAccept(_data, visitor);
}

// Get the variant as the specified type.
//
template <typename T>
FORCE_INLINE typename VariantConstAs<T>::type as() const {
return variantAs<typename VariantConstAs<T>::type>(_data);
}

template <typename T>
FORCE_INLINE operator T() const {
return variantAs<T>(_data);
}

FORCE_INLINE VariantConstRef getElement(size_t) const;

FORCE_INLINE VariantConstRef operator[](size_t index) const {
Expand Down

0 comments on commit ec43bf4

Please sign in to comment.