SkSpan.h 2.0 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061
  1. /*
  2. * Copyright 2018 Google Inc.
  3. *
  4. * Use of this source code is governed by a BSD-style license that can be
  5. * found in the LICENSE file.
  6. */
  7. #ifndef SkSpan_DEFINED
  8. #define SkSpan_DEFINED
  9. #include <cstddef>
  10. #include <string>
  11. #include <vector>
  12. #include "include/private/SkTo.h"
  13. template <typename T>
  14. class SkSpan {
  15. public:
  16. constexpr SkSpan() : fPtr{nullptr}, fSize{0} {}
  17. constexpr SkSpan(T* ptr, size_t size) : fPtr{ptr}, fSize{size} {}
  18. template <typename U, typename = typename std::enable_if<std::is_same<const U, T>::value>::type>
  19. constexpr SkSpan(const SkSpan<U>& that) : fPtr(that.data()), fSize{that.size()} {}
  20. constexpr SkSpan(const SkSpan& o) = default;
  21. constexpr SkSpan& operator=(const SkSpan& that) {
  22. fPtr = that.fPtr;
  23. fSize = that.fSize;
  24. return *this;
  25. }
  26. constexpr T& operator [] (size_t i) const { return fPtr[i]; }
  27. constexpr T& front() const { return fPtr[0]; }
  28. constexpr T& back() const { return fPtr[fSize - 1]; }
  29. constexpr T* begin() const { return fPtr; }
  30. constexpr T* end() const { return fPtr + fSize; }
  31. constexpr const T* cbegin() const { return fPtr; }
  32. constexpr const T* cend() const { return fPtr + fSize; }
  33. constexpr T* data() const { return fPtr; }
  34. constexpr size_t size() const { return fSize; }
  35. constexpr bool empty() const { return fSize == 0; }
  36. constexpr size_t size_bytes() const { return fSize * sizeof(T); }
  37. constexpr SkSpan<T> first(size_t prefixLen) { return SkSpan<T>{fPtr, prefixLen}; }
  38. private:
  39. T* fPtr;
  40. size_t fSize;
  41. };
  42. template <typename T, typename S>
  43. inline constexpr SkSpan<T> SkMakeSpan(T* p, S s) { return SkSpan<T>{p, SkTo<size_t>(s)}; }
  44. template <size_t N, typename T>
  45. inline constexpr SkSpan<T> SkMakeSpan(T(&a)[N]) { return SkSpan<T>{a, N}; }
  46. // This takes a const Container& to create an immutable span.
  47. template <typename Container>
  48. inline auto SkMakeSpan(const Container& c)
  49. -> SkSpan<typename std::remove_reference<decltype(*(c.data()))>::type> {
  50. return {c.data(), c.size()};
  51. }
  52. #endif // SkSpan_DEFINED