private:
typedef std::integral_constant<bool,
- boost::has_trivial_copy_constructor<T>::value &&
+ IsTriviallyCopyable<T>::value &&
sizeof(T) <= 16 // don't force large structures to be passed by value
> should_pass_by_value;
typedef typename std::conditional<
void M_destroy(T* p) noexcept {
if (usingStdAllocator::value) {
- if (!boost::has_trivial_destructor<T>::value) p->~T();
+ if (!std::is_trivially_destructible<T>::value)
+ p->~T();
} else {
std::allocator_traits<Allocator>::destroy(impl_, p);
}
// optimized
static void S_destroy_range(T* first, T* last) noexcept {
- if (!boost::has_trivial_destructor<T>::value) {
+ if (!std::is_trivially_destructible<T>::value) {
// EXPERIMENTAL DATA on fbvector<vector<int>> (where each vector<int> has
// size 0).
// The unrolled version seems to work faster for small to medium sized
/// use noexcept, you will have to wrap it in something that provides
/// the guarantee. We provide an alternate safe implementation for types
/// that don't use noexcept but that are marked folly::IsRelocatable
-/// and boost::has_nothrow_constructor, which is common for folly types.
+/// and std::is_nothrow_constructible, which is common for folly types.
/// In particular, if you can declare FOLLY_ASSUME_FBVECTOR_COMPATIBLE
/// then your type can be put in MPMCQueue.
///
/// enqueue using move construction, either real (if
/// is_nothrow_move_constructible) or simulated using relocation and
- /// default construction (if IsRelocatable and has_nothrow_constructor)
- template <typename = typename std::enable_if<
- (folly::IsRelocatable<T>::value &&
- boost::has_nothrow_constructor<T>::value) ||
- std::is_nothrow_constructible<T, T&&>::value>::type>
- void enqueue(const uint32_t turn,
- Atom<uint32_t>& spinCutoff,
- const bool updateSpinCutoff,
- T&& goner) noexcept {
+ /// default construction (if IsRelocatable and is_nothrow_constructible)
+ template <
+ typename = typename std::enable_if<
+ (folly::IsRelocatable<T>::value &&
+ std::is_nothrow_constructible<T>::value) ||
+ std::is_nothrow_constructible<T, T&&>::value>::type>
+ void enqueue(
+ const uint32_t turn,
+ Atom<uint32_t>& spinCutoff,
+ const bool updateSpinCutoff,
+ T&& goner) noexcept {
enqueueImpl(
turn,
spinCutoff,
CLEANFILES =
-
noinst_PROGRAMS = generate_fingerprint_tables
generate_fingerprint_tables_SOURCES = build/GenerateFingerprintTables.cpp
generate_fingerprint_tables_LDADD = libfollybase.la
} // namespace folly
-// Hook into boost's type traits
-namespace boost {
-template <class T>
-struct has_nothrow_constructor<folly::basic_fbstring<T> > : true_type {
- enum { value = true };
-};
-} // namespace boost
-
#include <folly/String-inl.h>
#include <bits/c++config.h>
#endif
-#include <boost/type_traits.hpp>
-
#define FOLLY_CREATE_HAS_MEMBER_TYPE_TRAITS(classname, type_name) \
template <typename TTheClass_> \
struct classname##__folly_traits_impl__ { \
struct IsRelocatable< __VA_ARGS__ > : std::true_type {};
/**
- * Use this macro ONLY inside namespace boost. When using it with a
- * regular type, use it like this:
- *
- * // Make sure you're at namespace ::boost scope
- * template<> FOLLY_ASSUME_HAS_NOTHROW_CONSTRUCTOR(MyType)
- *
- * When using it with a template type, use it like this:
- *
- * // Make sure you're at namespace ::boost scope
- * template<class T1, class T2>
- * FOLLY_ASSUME_HAS_NOTHROW_CONSTRUCTOR(MyType<T1, T2>)
- */
-#define FOLLY_ASSUME_HAS_NOTHROW_CONSTRUCTOR(...) \
- struct has_nothrow_constructor< __VA_ARGS__ > : ::boost::true_type {};
-
-/**
- * The FOLLY_ASSUME_FBVECTOR_COMPATIBLE* macros below encode two
- * assumptions: first, that the type is relocatable per IsRelocatable
- * above, and that it has a nothrow constructor. Most types can be
- * assumed to satisfy both conditions, but it is the responsibility of
- * the user to state that assumption. User-defined classes will not
- * work with fbvector (see FBVector.h) unless they state this
- * combination of properties.
+ * The FOLLY_ASSUME_FBVECTOR_COMPATIBLE* macros below encode the
+ * assumption that the type is relocatable per IsRelocatable
+ * above. Many types can be assumed to satisfy this condition, but
+ * it is the responsibility of the user to state that assumption.
+ * User-defined classes will not be optimized for use with
+ * fbvector (see FBVector.h) unless they state that assumption.
*
* Use FOLLY_ASSUME_FBVECTOR_COMPATIBLE with regular types like this:
*
*/
// Use this macro ONLY at global level (no namespace)
-#define FOLLY_ASSUME_FBVECTOR_COMPATIBLE(...) \
- namespace folly { template<> FOLLY_ASSUME_RELOCATABLE(__VA_ARGS__) } \
- namespace boost { \
- template<> FOLLY_ASSUME_HAS_NOTHROW_CONSTRUCTOR(__VA_ARGS__) }
+#define FOLLY_ASSUME_FBVECTOR_COMPATIBLE(...) \
+ namespace folly { \
+ template <> \
+ FOLLY_ASSUME_RELOCATABLE(__VA_ARGS__) \
+ }
// Use this macro ONLY at global level (no namespace)
-#define FOLLY_ASSUME_FBVECTOR_COMPATIBLE_1(...) \
- namespace folly { \
- template <class T1> FOLLY_ASSUME_RELOCATABLE(__VA_ARGS__<T1>) } \
- namespace boost { \
- template <class T1> FOLLY_ASSUME_HAS_NOTHROW_CONSTRUCTOR(__VA_ARGS__<T1>) }
+#define FOLLY_ASSUME_FBVECTOR_COMPATIBLE_1(...) \
+ namespace folly { \
+ template <class T1> \
+ FOLLY_ASSUME_RELOCATABLE(__VA_ARGS__<T1>) \
+ }
// Use this macro ONLY at global level (no namespace)
-#define FOLLY_ASSUME_FBVECTOR_COMPATIBLE_2(...) \
- namespace folly { \
- template <class T1, class T2> \
- FOLLY_ASSUME_RELOCATABLE(__VA_ARGS__<T1, T2>) } \
- namespace boost { \
- template <class T1, class T2> \
- FOLLY_ASSUME_HAS_NOTHROW_CONSTRUCTOR(__VA_ARGS__<T1, T2>) }
+#define FOLLY_ASSUME_FBVECTOR_COMPATIBLE_2(...) \
+ namespace folly { \
+ template <class T1, class T2> \
+ FOLLY_ASSUME_RELOCATABLE(__VA_ARGS__<T1, T2>) \
+ }
// Use this macro ONLY at global level (no namespace)
-#define FOLLY_ASSUME_FBVECTOR_COMPATIBLE_3(...) \
- namespace folly { \
- template <class T1, class T2, class T3> \
- FOLLY_ASSUME_RELOCATABLE(__VA_ARGS__<T1, T2, T3>) } \
- namespace boost { \
- template <class T1, class T2, class T3> \
- FOLLY_ASSUME_HAS_NOTHROW_CONSTRUCTOR(__VA_ARGS__<T1, T2, T3>) }
+#define FOLLY_ASSUME_FBVECTOR_COMPATIBLE_3(...) \
+ namespace folly { \
+ template <class T1, class T2, class T3> \
+ FOLLY_ASSUME_RELOCATABLE(__VA_ARGS__<T1, T2, T3>) \
+ }
// Use this macro ONLY at global level (no namespace)
-#define FOLLY_ASSUME_FBVECTOR_COMPATIBLE_4(...) \
- namespace folly { \
- template <class T1, class T2, class T3, class T4> \
- FOLLY_ASSUME_RELOCATABLE(__VA_ARGS__<T1, T2, T3, T4>) } \
- namespace boost { \
- template <class T1, class T2, class T3, class T4> \
- FOLLY_ASSUME_HAS_NOTHROW_CONSTRUCTOR(__VA_ARGS__<T1, T2, T3, T4>) }
+#define FOLLY_ASSUME_FBVECTOR_COMPATIBLE_4(...) \
+ namespace folly { \
+ template <class T1, class T2, class T3, class T4> \
+ FOLLY_ASSUME_RELOCATABLE(__VA_ARGS__<T1, T2, T3, T4>) \
+ }
/**
* Instantiate FOLLY_ASSUME_FBVECTOR_COMPATIBLE for a few types. It is
FOLLY_NAMESPACE_STD_END
-namespace boost {
-
-template <class T> class shared_ptr;
-
-template <class T, class U>
-struct has_nothrow_constructor< std::pair<T, U> >
- : std::integral_constant<bool,
- has_nothrow_constructor<T>::value &&
- has_nothrow_constructor<U>::value> {};
-
-} // namespace boost
-
namespace folly {
// STL commonly-used types
FOLLY_ASSUME_FBVECTOR_COMPATIBLE_2(std::unique_ptr)
FOLLY_ASSUME_FBVECTOR_COMPATIBLE_1(std::shared_ptr)
FOLLY_ASSUME_FBVECTOR_COMPATIBLE_1(std::function)
-
-// Boost
-FOLLY_ASSUME_FBVECTOR_COMPATIBLE_1(boost::shared_ptr)
#endif
/* Some combinations of compilers and C++ libraries make __int128 and
If you don't do this, `fbvector<Widget>` will fail to compile
with a `static_assert`.
-#### Additional Constraints
-
-Similar improvements are possible in presence of a "simple" type
-- more specifically, one that has a trivial assignment (i.e.
-assignment is the same as bitblitting the bits over) or a nothrow
-default constructor. These traits are used gainfully by
-`fbvector` in a variety of places. Fortunately, these traits are
-already present in the C++ standard (well, currently in Boost).
-To summarize, in order to work with `fbvector`, a type `Widget`
-must pass:
-
- static_assert(
- IsRelocatable<Widget>::value &&
- (boost::has_trivial_assign<T>::value ||
- boost::has_nothrow_constructor<T>::value),
- "");
-
-These traits go hand in hand; for example, it would be very
-difficult to design a class that satisfies one branch of the
-conjunction above but not the other. `fbvector` uses these simple
-constraints to minimize the number of copies made on many common
-operations such as `push_back`, `insert`, or `resize`.
-
-To make it easy for you to state assumptions about a given type
-or family of parameterized types, check Traits.h and in
-particular handy family of macros FOLLY_ASSUME_FBVECTOR_COMPATIBLE*.
-
### Miscellaneous
***
'folly/Traits.h'
-----------------
-Implements traits complementary to those provided in <boost/type_traits.h>
+Implements traits complementary to those provided in <type_traits>
* Implements `IsRelocatable` trait.
* Implements `IsOneOf` trait
### Motivation
***
-`<boost/type_traits.hpp>` is the Boost type-traits library defining a
-variety of traits such as `is_integral` or `is_floating_point`. This helps
-to gain more information about a given type.
-Many traits introduced by Boost have been standardized in C++11.
+`<type_traits>` is the Standard type-traits library defining a variety of traits
+such as `is_integral` or `is_floating_point`. This helps to gain more
+information about a given type.
-`folly/Traits.h` implements traits complementing those present in boost.
+`folly/Traits.h` implements traits complementing those present in the Standard.
### IsRelocatable
namespace folly {
// defining specialization of IsRelocatable for MySimpleType
template <>
- struct IsRelocatable<MySimpleType> : boost::true_type {};
+ struct IsRelocatable<MySimpleType> : std::true_type {};
// defining specialization of IsRelocatable for MyParameterizedType
template <class T1, class T2>
struct IsRelocatable<MyParameterizedType<T1, T2>>
- : ::boost::true_type {};
+ : ::std::true_type {};
}
```
}
```
- * Stating that a type has no throw constructor using a macro
-
- ```Cpp
- namespace boost {
- // For a Regular Type
- FOLLY_ASSUME_HAS_NOTHROW_CONSTRUCTOR(MySimpleType);
- // For a Parameterized Type
- FOLLY_ASSUME_HAS_NOTHROW_CONSTRUCTOR(MyParameterizedType<T1, T2>);
- }
- ```
-
`fbvector` only works with relocatable objects. If assumptions are not stated
explicitly, `fbvector<MySimpleType>` or `fbvector<MyParameterizedType>`
will fail to compile due to assertion below:
Few common types, namely `std::basic_string`, `std::vector`, `std::list`,
`std::map`, `std::deque`, `std::set`, `std::unique_ptr`, `std::shared_ptr`,
-`std::function`, `boost::shared_ptr` which are compatible with `fbvector` are
-already instantiated and declared compatible with `fbvector`. `fbvector` can be
-directly used with any of these C++ types.
+`std::function`, which are compatible with `fbvector` are already instantiated
+and declared compatible with `fbvector`. `fbvector` can be directly used with
+any of these C++ types.
`std::pair` can be safely assumed to be compatible with `fbvector` if both of
its components are.
### IsOneOf
***
-`boost::is_same<T1, T2>::value` can be used to test if types of T1 and T2 are
-same. `folly::IsOneOf<T, T1, Ts...>::value` can be used to test if type of T1
+`std::is_same<T1, T2>::value` can be used to test if types of T1 and T2 are
+same. `folly::IsOneOf<T, T1, Ts...>::value` can be used to test if type of T1
matches the type of one of the other template parameter, T1, T2, ...Tn.
Recursion is used to implement this type trait.