Completed
Push — master ( a5119c...b82fec )
by John
11:27
created

ArrayList::offsetSet()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 8
Code Lines 5

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 1
Metric Value
c 1
b 0
f 1
dl 0
loc 8
rs 9.4285
cc 2
eloc 5
nc 2
nop 2
1
<?php
2
namespace Jmw\Collection\Lists;
3
4
use Jmw\Collection\CollectionInterface;
5
use Jmw\Collection\Exception\InvalidTypeException;
6
use Jmw\Collection\Exception\IndexOutOfBoundsException;
7
use Jmw\Collection\CollectionAbstract;
8
9
/**
10
 * This is the most generic collection type
11
 * It uses a simple PHP array as its underlying data
12
 * store, and PHP functions for most of the operations.
13
 * @author john
14
 *
15
 */
16
class ArrayList extends CollectionAbstract implements ListInterface
17
{
18
	/**
19
	 * Underlying data store
20
	 * @var array
21
	 */
22
	protected $array;
23
	
24
	/**
25
	 * Constructs an ArrayList
26
	 * Defaults with the given array
27
	 * @param array $array
28
	 */
29
	public function __construct($array = [])
30
	{
31
		if(!is_array($array))
32
		{
33
			throw new InvalidTypeException('array', gettype($array));
0 ignored issues
show
Documentation introduced by
'array' is of type string, but the function expects a object<Jmw\Collection\Exception\multitype>.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
Documentation introduced by
gettype($array) is of type string, but the function expects a object<Jmw\Collection\Exception\multitype>.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
34
		}
35
		$this->array = array_values($array);
36
	}
37
	
38
	/**
39
	 * Appends the specified element to the end of this list.
40
	 * @param multitype $element
41
	 * @return void
42
	 */
43
	public function add($element)
44
	{
45
		$this->array[] = $element;
46
	}
47
	
48
	/**
49
	 * Inserts the specified element at the specified position in this list.
50
	 * @param int $index
51
	 * @param multitype $element
52
	 * @return void
53
	 */
54
	public function addAt($index, $element)
55
	{
56
		$this->checkInt($index);
57
		//element has to be wrapped in array sintax in case it is an object or an array or null
58
		array_splice($this->array, $index, 0, [$element]);
59
	}
60
	
61
	/**
62
	 * Removes all of the elements from this list.
63
	 * @return void
64
	 */
65
	public function clear()
66
	{
67
		$this->array = [];
68
	}
69
	
70
	/**
71
	 * Compares the specified object with this list for equality.
72
	 * @param multitype $object
73
	 * @return boolean
74
	 */
75
	public function equals($object)
76
	{
77
		if($object instanceof ListInterface && $object->size() === $this->size())
78
		{
79
			foreach ($object->toArray() as $index=>$element)
80
			{
81
				if($element !== $this->array[$index])
82
				{
83
					return false;
84
				}
85
			}
86
			return true;
87
		}
88
		
89
		return false;
90
	}
91
	
92
	/**
93
	 * Returns the element at the specified position in this list.
94
	 * @param int $index
95
	 * @return multitype
96
	 */
97 View Code Duplication
	public function get($index)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
98
	{
99
		$this->checkInt($index);
100
		if(!array_key_exists($index, $this->array))
101
		{
102
			throw new IndexOutOfBoundsException($index);
103
		}
104
		return $this->array[$index];
105
	}
106
	
107
	/**
108
	 * Returns the index of the first occurrence of the 
109
	 * specified element in this list, 
110
	 * or -1 if this list does not contain the element.
111
	 * @param multitype $element
112
	 * @return int
113
	 */
114
	public function indexOf($element)
115
	{
116
		$index = array_search($element, $this->array, true);
117
		
118
		$index = $index === false ? -1 : $index;
119
		
120
		return $index;
121
	}
122
	
123
	/**
124
	 * Returns an iterator over the elements in this list in proper sequence.
125
	 * @return IteratorInterface
126
	 */
127
	public function iterator()
128
	{
129
		return $this->listIterator();
130
	}
131
	
132
	/**
133
	 * Returns the index of the last occurrence of the 
134
	 * specified element in this list, 
135
	 * or -1 if this list does not contain the element.
136
	 * @param multitype $element
137
	 * @return int
138
	 */
139
	public function lastIndexOf($element)
140
	{		
141
		$index = array_search($element, array_reverse($this->array), true);
142
		
143
		if($index === false)
144
		{
145
			$index = -1;
146
		}
147
		else
148
		{
149
			$index = $this->size() - $index - 1;
150
		}
151
152
		return $index;
153
	}
154
	
155
	/**
156
	 * Returns a list iterator over the elements 
157
	 * in this list (in proper sequence).
158
	 * @return ListIterator
159
	 */
160
	public function listIterator()
161
	{
162
		return new ListIterator($this);
163
	}
164
	
165
	/**
166
	 * Returns a list iterator over the elements in this list (in proper sequence), 
167
	 * starting at the specified position in the list.
168
	 * @param int $index
169
	 * @return ListIterator
170
	 */
171
	public function listIteratorAt($index)
172
	{
173
		return new ListIterator($this, $index);
174
	}
175
	
176
	/**
177
	 * Removes the first occurrence of the specified element 
178
	 * from this list, if it is present 
179
	 * @param multitype $element
180
	 * @return boolean
181
	 * @throws IndexOutOfBoundsException
182
	 */
183
	public function remove($element)
184
	{
185
		$index = $this->indexOf($element);
186
		
187
		if($index === -1)
188
		{
189
			return false;
190
		}
191
		
192
		return $this->removeAt($index);
193
	}
194
	
195
	/**
196
	 * Removes from this list all of its elements that
197
	 * are contained in the specified collection
198
	 * @param CollectionInterface $collection
199
	 * @return void 
200
	 */
201
	public function removeAll(CollectionInterface $collection)
202
	{
203
		$this->array = array_values(array_diff($this->array, $collection->toArray()));
204
	}
205
	
206
	/**
207
	 * Removes the element at the specified 
208
	 * position in this list (optional operation).
209
	 * @param int $index
210
	 * @return boolean
211
	 * @throws IndexOutOfBoundsException
212
	 */
213
	public function removeAt($index)
214
	{
215
		$this->checkInt($index);
216
		if($index < 0 || $index > $this->size())
217
		{
218
			throw new IndexOutOfBoundsException($index);
219
		}
220
		else
221
		{
222
			unset($this->array[$index]);
223
			$this->array = array_values($this->array);
224
		}
225
		return true;
226
	}
227
	
228
	/**
229
	 * Removes from this list all of the elements whose index is between 
230
	 * from, inclusive, and to, exclusive.
231
	 * @param int $from
232
	 * @param int $to
233
	 * @return void
234
	 */
235
	public function removeRange($from, $to)
236
	{
237
		array_splice($this->array, $from, $to - $from);
238
	}
239
240
	/**
241
	 * Replaces the element at the specified position
242
	 * in this list with the specified element.
243
	 * @param int $index
244
	 * @param int $element
245
	 * @return void
246
	 * @throws IndexOutOfBoundsException
247
	 */
248 View Code Duplication
	public function set($index, $element)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
249
	{
250
		if(array_key_exists($index, $this->array))
251
		{
252
			$this->array[$index] = $element;
253
		}
254
		else
255
		{
256
			throw new IndexOutOfBoundsException($index);
257
		}
258
	}
259
	
260
	/**
261
	 * Returns the number of elements in this list.
262
	 * @return int
263
	 */
264
	public function size()
265
	{
266
		return count($this->array);
267
	}
268
	
269
	/**
270
	 * Returns a view of the portion of this list between the 
271
	 * specified from, inclusive, and to, exclusive.
272
	 * @param int $from
273
	 * @param int $to
274
	 * @return ArrayList
275
	 */
276
	public function subList($from, $to)
277
	{
278
		$this->checkInt($from);
279
		$this->checkInt($to);
280
		return new ArrayList(array_slice($this->array, $from, $to - $from));
281
	}
282
	
283
	/**
284
	 * Returns an array containing all of the elements in this list
285
	 * in proper sequence (from first to last element).
286
	 * @return array
287
	 */
288
	public function toArray()
289
	{
290
		return $this->array;
291
	}
292
	
293
	/**
294
	 * Returns the hash code value for this collection.
295
	 * @return string
296
	 */
297
	public function hashCode()
298
	{
299
		return spl_object_hash($this);
300
	}
301
	
302
	/**
303
	 * Checks to see if a variable is an int.
304
	 * This is meant to help ensure that all indexes
305
	 * remain integers.
306
	 * @param int $var
307
	 * @throws InvalidTypeException
308
	 */
309
	protected function checkInt($var)
310
	{
311
		if(!is_int($var))
312
		{
313
			throw new InvalidTypeException('int', gettype($var));
0 ignored issues
show
Documentation introduced by
'int' is of type string, but the function expects a object<Jmw\Collection\Exception\multitype>.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
Documentation introduced by
gettype($var) is of type string, but the function expects a object<Jmw\Collection\Exception\multitype>.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
314
		}
315
	}
316
	
317
	/*********************************************
318
	 ** Array Access Methods
319
	 *********************************************/
320
321
	/**
322
	 *
323
	 * {@inheritDoc}
324
	 * @see ArrayAccess::offsetExists()
325
	 */
326 View Code Duplication
	public function offsetExists($offset)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
327
	{
328
		if(!is_int($offset) || $offset >= $this->size() || $offset < 0) {
329
			return false;
330
		} else {
331
			return true;
332
		}
333
	}
334
	
335
	/**
336
	 *
337
	 * {@inheritDoc}
338
	 * @see ArrayAccess::offsetGet()
339
	 */
340
	public function offsetGet($offset)
341
	{
342
		return $this->get($offset);
343
	}
344
	
345
	/**
346
	 *
347
	 * {@inheritDoc}
348
	 * @see ArrayAccess::offsetSet()
349
	 */
350
	public function offsetSet($offset, $value)
351
	{
352
		if($offset === null) {
353
			$this->add($value);
354
		} else {
355
			$this->addAt($offset, $value);
356
		}
357
	}
358
	
359
	/**
360
	 *
361
	 * {@inheritDoc}
362
	 * @see ArrayAccess::offsetUnset()
363
	 */
364
	public function offsetUnset($offset)
365
	{
366
		$this->removeAt($offset);
367
	}
368
}