source: trunk/ab5.0/ablib/src/Classes/System/Collections/Generic/List.ab@ 587

Last change on this file since 587 was 587, checked in by dai, 16 years ago

型パラメータの指定し忘れを修正(本来はエラーとして扱うべき … #190)。

File size: 6.3 KB
Line 
1
2Namespace System
3Namespace Collections
4Namespace Generic
5
6Namespace Detail
7 Class PointerEnumerator<T>
8 Implements IEnumerator<T>
9 Public
10 Sub PointerEnumerator(ptr As *T, count As Long)
11 p = ptr
12 n = count
13 cur = -1
14 End Sub
15
16 Function MoveNext() As Boolean
17 cur++
18 MoveNext = (cur <> n)
19 End Function
20
21 Sub Reset()
22 n = -1
23 End Sub
24
25 Function Current() As T
26 Current = p[cur]
27 End Function
28
29 Virtual Sub Dispose()
30 p = NULL
31 n = 0
32 cur = -1
33 End Sub
34 Private
35 p As *T
36 n As Long
37 cur As Long
38 End Class
39End Namespace
40
41Class List<T>
42 Inherits IList<T>
43
44 items As *T
45 capacity As Long
46 count As Long
47
48 Sub Realloc( allocateSize As Long )
49 items = realloc( items, allocateSize * SizeOf(T) )
50 capacity = allocateSize
51 End Sub
52
53 Sub _Initialize( capacity As Long )
54 This.items = GC_malloc( capacity * SizeOf(T) )
55 This.capacity = capacity
56 End Sub
57
58 Sub SetLeastCapacity( capacity As Long )
59 If This.capacity < capacity Then
60 Realloc(capacity)
61 End If
62 End Sub
63Public
64 Sub List()
65 _Initialize(16)
66 End Sub
67
68 /*!
69 @brief 予め要素数を指定してList<T>を初期化
70 @author NoWest
71 @date 2008/07/13
72 @param リストの要素数
73 */
74 Sub List( capacity As Long )
75 _Initialize( capacity )
76 End Sub
77
78 /*!
79 @brief 既存の配列List<T>を初期化
80 @author NoWest
81 @date 2008/07/13
82 @param インデックス
83 */
84 Sub List( array As *T, length As Long )
85 _Initialize( length )
86
87 memmove( This.items, array, length * SizeOf(T) )
88 This.count = length
89 End Sub
90
91 /*!
92 @brief インデクサ
93 @author Daisuke Yamamoto
94 @date 2007/08/22
95 @param インデックス
96 */
97 Override Sub Operator[] ( index As Long, item As T )
98 Item[index] = item
99 End Sub
100 Override Function Operator[] ( index As Long ) As T
101 Return Item[index]
102 End Function
103
104 /*!
105 @brief インデクサ
106 @author Egtra
107 @date 2008/08/04
108 @param インデックス
109 */
110 Override Sub Item( index As Long, item As T )
111 If 0 <= index And index < capacity Then
112 items[index]=item
113 Else
114 Throw New ArgumentOutOfRangeException("index")
115 End If
116 End Sub
117 Override Function Item( index As Long ) As T
118 If 0 <= index And index < capacity Then
119 Return items[index]
120 Else
121 Throw New ArgumentOutOfRangeException("index")
122 End If
123 End Function
124 /*!
125 @brief ポインタ型へのキャスト
126 @author Daisuke Yamamoto
127 @date 2007/08/22
128 @param インデックス
129 */
130 Function Operator() As *T
131 Return items
132 End Function
133
134
135 '----------------------------------------------------------------
136 ' パブリック プロパティ
137 '----------------------------------------------------------------
138
139 /*!
140 @brief Listに格納されている要素の数を取得する
141 @author Daisuke Yamamoto
142 @date 2007/08/22
143 */
144 Override Function Count() As Long
145 Return This.count
146 End Function
147
148 Const Function Capacity() As Long
149 Return This.capacity
150 End Function
151
152 Sub Capacity(c As Long)
153 If c <> capacity Then
154 If c < capacity Then
155 Throw New ArgumentOutOfRangeException("capacity")
156 Else
157 Realloc(c)
158 End If
159 End If
160 End Sub
161
162 /*!
163 @brief Listが読み込み専用かどうかを取得する
164 @author NoWest
165 @date 2008/07/12
166 */
167 Override Function IsReadOnly() As Boolean
168 Return False
169 End Function
170
171 '----------------------------------------------------------------
172 ' パブリック メソッド
173 '----------------------------------------------------------------
174
175 /*!
176 @brief Listの末端に要素を追加する
177 @author Daisuke Yamamoto
178 @date 2007/08/22
179 @param 追加するオブジェクト
180 */
181 Override Sub Add( item As T )
182 SetLeastCapacity(This.count + 1)
183 This.items[ This.count ] = item
184 This.count++
185 End Sub
186
187' Function AsReadOnly() As ReadOnlyCollection
188
189 /*!
190 @brief Listからすべての要素を削除する
191 @author Daisuke Yamamoto
192 @date 2007/08/22
193 */
194 Override Sub Clear()
195 This.count = 0
196 End Sub
197
198/* Override Function Contains ( item As T ) As Boolean
199 TODO
200 End Function*/
201
202 /*!
203 @brief List内から、最初に出現する値のインデックスを取得する
204 @author Daisuke Yamamoto
205 @date 2007/08/22
206 @return インデックス(見つからなかったときは-1)
207 */
208 Override Function IndexOf( item As T ) As Long
209 Dim i As Long
210 For i = 0 To ELM( This.count )
211 If items[i].Equals(item) Then
212 Return i
213 End If
214 Next
215 Return -1
216 End Function
217
218 /*!
219 @brief List内の指定したインデックスの位置に要素を挿入する
220 @author Daisuke Yamamoto
221 @date 2007/08/22
222 */
223 Override Sub Insert( index As Long, item As T )
224 SetLeastCapacity(This.count + 1)
225 memmove( items + (index+1)*SizeOf(T), items + index*SizeOf(T), (This.count - index)*SizeOf(T) )
226 items[index] = item
227 This.count++
228 End Sub
229
230 /*!
231 @brief List内で最初に出現する値を削除する
232 @author Daisuke Yamamoto
233 @date 2007/09/28
234 @return 値が削除されたときはTrue、されなかったときはFlaseが返る
235 */
236 Override Function Remove( item As T ) As Boolean
237 Dim index = IndexOf( item )
238 If index = -1 Then
239 Return False
240 End If
241
242 removeAtImpl( index )
243 Return True
244 End Function
245
246 /*!
247 @brief List内の指定したインデックスの要素を削除する
248 @author Daisuke Yamamoto
249 @date 2007/10/03
250 */
251 Override Sub RemoveAt( index As Long )
252 If 0 <= index And index < capacity Then
253 removeAtImpl( index )
254 Else
255 Throw New ArgumentOutOfRangeException("index")
256 End If
257 End Sub
258Private
259 Sub removeAtImpl( index As Long )
260 memmove( items + index*SizeOf(T), items + (index+1)*SizeOf(T), (This.count - (index+1))*SizeOf(T) )
261 This.count--
262 End Sub
263
264Public
265
266 /*!
267 @brief Listの要素を文字列で返す
268 @author OverTaker
269 @date 2008/6/26
270 @return 文字列
271 */
272 Override Function ToString() As String
273 Dim string = New Text.StringBuilder
274 Dim i As Long
275 For i = 0 To ELM( This.count )
276 string.Append(This[i]).Append(Ex"\r\n")
277 Next
278 Return string.ToString
279 End Function
280
281 /*!
282 @brief 実際の要素数が現在の容量の 90% 未満の場合は、容量をその数に設定します
283 @author NoWest
284 @date 2008/07/20
285 */
286 Sub TrimExcess ()
287 If ( This.capacity ) * 0.9 > This.count Then
288 Realloc( This.count )
289 End If
290 End Sub
291
292 /*!
293 @brief IEnumeratorインターフェイスを取得する
294 @author Daisuke Yamamoto
295 @date 2007/11/19
296 @return IEnumeratorインターフェイスが返る
297 */
298 Override Function GetEnumerator() As IEnumerator<T>
299 Return New Detail.PointerEnumerator<T>(items, count)
300 End Function
301End Class
302
303
304End Namespace
305End Namespace
306End Namespace
Note: See TracBrowser for help on using the repository browser.