summaryrefslogtreecommitdiffstats
path: root/source/core/array-view.h
blob: 193aedbbb580d343b9b75fe355bfc3248530fb8b (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
#ifndef CORE_LIB_ARRAY_VIEW_H
#define CORE_LIB_ARRAY_VIEW_H

#include "exception.h"

namespace Slang
{
	template<typename T>
	class ArrayView
	{
	private:
		T * _buffer;
		int _count;
		int stride;
	public:
		T* begin() const
		{
			return _buffer;
		}
		T* end() const
		{
			return (T*)((char*)_buffer + _count*stride);
		}
	public:
		ArrayView()
		{
			_buffer = 0;
			_count = 0;
		}
		ArrayView(const T & singleObj)
		{
			SetData((T*)&singleObj, 1, sizeof(T));
		}
		ArrayView(T * buffer, int count)
		{
			SetData(buffer, count, sizeof(T));
		}
		ArrayView(void * buffer, int count, int _stride)
		{
			SetData(buffer, count, _stride);
		}
		void SetData(void * buffer, int count, int _stride)
		{
			this->_buffer = (T*)buffer;
			this->_count = count;
			this->stride = _stride;
		}
		inline int GetCapacity() const
		{
			return _count;
		}
		inline int Count() const
		{
			return _count;
		}

		inline T & operator [](int id) const
		{
#if _DEBUG
			if (id >= _count || id < 0)
				throw IndexOutofRangeException("Operator[]: Index out of Range.");
#endif
			return *(T*)((char*)_buffer+id*stride);
		}

		inline T* Buffer() const
		{
			return _buffer;
		}

		template<typename T2>
		int IndexOf(const T2 & val) const
		{
			for (int i = 0; i < _count; i++)
			{
				if (*(T*)((char*)_buffer + i*stride) == val)
					return i;
			}
			return -1;
		}

		template<typename T2>
		int LastIndexOf(const T2 & val) const
		{
			for (int i = _count - 1; i >= 0; i--)
			{
				if (*(T*)((char*)_buffer + i*stride) == val)
					return i;
			}
			return -1;
		}

		template<typename Func>
		int FindFirst(const Func & predicate) const
		{
			for (int i = 0; i < _count; i++)
			{
				if (predicate(_buffer[i]))
					return i;
			}
			return -1;
		}

		template<typename Func>
		int FindLast(const Func & predicate) const
		{
			for (int i = _count - 1; i >= 0; i--)
			{
				if (predicate(_buffer[i]))
					return i;
			}
			return -1;
		}
	};

	template<typename T>
	ArrayView<T> MakeArrayView(const T & obj)
	{
		return ArrayView<T>(obj);
	}
		
	template<typename T>
	ArrayView<T> MakeArrayView(T * buffer, int count)
	{
		return ArrayView<T>(buffer, count);
	}
}

#endif