Completed
Pull Request — master (#6)
by Carlos C
02:44
created

DequeCommonMethods::checkElementAdd()   B

Complexity

Conditions 6
Paths 4

Size

Total Lines 24
Code Lines 14

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 18
CRAP Score 6

Importance

Changes 1
Bugs 0 Features 0
Metric Value
c 1
b 0
f 0
dl 0
loc 24
ccs 18
cts 18
cp 1
rs 8.5125
cc 6
eloc 14
nc 4
nop 1
crap 6
1
<?php namespace GenericCollections\Traits;
2
3
use GenericCollections\Exceptions\ContainerIsEmptyException;
4
use GenericCollections\Exceptions\ContainerDoesNotAllowNullException;
5
use GenericCollections\Exceptions\ContainerNotUniqueMemberException;
6
use GenericCollections\Exceptions\InvalidElementTypeException;
7
use GenericCollections\Internal\DoubleLinkedList;
8
9
/**
10
 * This trait include all deque standard methods to queue, stack and deque
11
 *
12
 * @property DoubleLinkedList $storage
13
 *
14
 * @package GenericCollections\Traits
15
 */
16
trait DequeCommonMethods
17
{
18
    /**
19
     * This function must return the container internal name, like 'deque', 'queue' or 'stack'
20
     * @return string
21
     */
22
    abstract protected function containerInternalName();
23
24
    /**
25
     * @see \GenericCollections\Interfaces\BaseOptions::optionAllowNullMembers
26
     * @return bool
27
     */
28
    abstract public function optionAllowNullMembers();
29
30
    /**
31
     * @see \GenericCollections\Interfaces\BaseOptions::optionUniqueValues
32
     * @return bool
33
     */
34
    abstract public function optionUniqueValues();
35
36
    /**
37
     * @see \GenericCollections\Interfaces\BaseOptions::optionComparisonIsIdentical
38
     * @return bool
39
     */
40
    abstract public function optionComparisonIsIdentical();
41
42
    /**
43
     * @see \GenericCollections\Interfaces\BaseCollectionInterface::checkElementType
44
     * @param mixed $element
45
     * @return bool
46
     */
47
    abstract public function checkElementType($element);
48
49
    /**
50
     * @see \GenericCollections\Interfaces\BaseCollectionInterface::getElementType
51
     * @return string
52
     */
53
    abstract public function getElementType();
54
55
    /**
56
     * @see \GenericCollections\Internal\StorageInterface::isEmpty
57
     * @return bool
58
     */
59
    abstract public function isEmpty();
60
61
    /**
62
     * Throw an exception when add a non valid element
63
     *
64
     * @param $element
65
     */
66 72
    private function checkElementAdd($element)
67
    {
68
        // always throw an exception if element is null and container does not allow nulls
69 72
        if (! $this->optionAllowNullMembers() && is_null($element)) {
70 8
            throw new ContainerDoesNotAllowNullException(
71 8
                $this->containerInternalName(),
72 8
                get_class($this)
73 8
            );
74
        }
75
        // always throw an exception if element is not the correct type
76 64
        if (! $this->checkElementType($element)) {
77 6
            throw new InvalidElementTypeException(
78 6
                $this->containerInternalName(),
79 6
                $this->getElementType(),
80 6
                get_class($this)
81 6
            );
82
        }
83 58
        if ($this->optionUniqueValues() && $this->contains($element)) {
84 6
            throw new ContainerNotUniqueMemberException(
85 6
                $this->containerInternalName(),
86 6
                get_class($this)
87 6
            );
88
        }
89 58
    }
90
91
    /**
92
     * Throw an exception when add a non valid element
93
     *
94
     * @param $element
95
     * @return bool
96
     */
97 20
    private function checkElementOffer($element)
98
    {
99
        try {
100 20
            $this->checkElementAdd($element);
101 20
        } catch (ContainerNotUniqueMemberException $ex) {
102 3
            return false;
103
        }
104 11
        return true;
105
    }
106
107 12
    public function addFirst($element)
108
    {
109 12
        $this->checkElementAdd($element);
110 8
        $this->storage->unshift($element);
111 8
    }
112
113 52
    public function addLast($element)
114
    {
115 52
        $this->checkElementAdd($element);
116 47
        $this->storage->push($element);
117 47
    }
118
119 7
    public function offerFirst($element)
120
    {
121 7
        if (! $this->checkElementOffer($element)) {
122 1
            return false;
123
        }
124 4
        $this->storage->unshift($element);
125 4
        return true;
126
    }
127
128 13
    public function offerLast($element)
129
    {
130 13
        if (! $this->checkElementOffer($element)) {
131 2
            return false;
132
        }
133 7
        $this->storage->push($element);
134 7
        return true;
135
    }
136
137 8
    public function getFirst()
138
    {
139 8
        if ($this->isEmpty()) {
140 2
            throw new ContainerIsEmptyException($this->containerInternalName(), 'get');
141
        }
142 6
        return $this->storage->bottom();
143
    }
144
145 2
    public function peekFirst()
146
    {
147 2
        if ($this->isEmpty()) {
148 2
            return null;
149
        }
150 2
        return $this->storage->bottom();
151
    }
152
153 6
    public function removeFirst()
154
    {
155 6
        if ($this->isEmpty()) {
156 2
            throw new ContainerIsEmptyException($this->containerInternalName(), 'remove');
157
        }
158 4
        return $this->storage->shift();
159
    }
160
161 4
    public function pollFirst()
162
    {
163 4
        if ($this->isEmpty()) {
164 2
            return null;
165
        }
166 4
        return $this->storage->shift();
167
    }
168
169 9
    public function contains($element)
170
    {
171 9
        return $this->storage->contains($element);
172
    }
173
174 81
    protected function createStorageObject()
175
    {
176 81
        $this->storage = new DoubleLinkedList();
177 81
        if (! $this->optionComparisonIsIdentical()) {
178 2
            $this->storage->strictComparisonOff();
179 2
        }
180 81
    }
181
}
182