Passed
Push — master ( 412239...139af3 )
by Stephen
01:00 queued 12s
created

ArrayHelpers::arrayPop()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 10
Code Lines 3

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 3
nc 1
nop 1
dl 0
loc 10
rs 10
c 0
b 0
f 0
1
<?php
2
3
namespace Sfneal\Helpers\Arrays;
4
5
class ArrayHelpers
6
{
7
    // todo: remove 'array' prefix from method names
8
9
    /**
10
     * @var array
11
     */
12
    private $array;
13
14
    /**
15
     * ArrayHelpers constructor.
16
     *
17
     * @param array $array
18
     */
19
    public function __construct(array $array)
20
    {
21
        $this->array = $array;
22
    }
23
24
    /**
25
     * Returns a chunked array with calculated chunk size.
26
     *
27
     * @param int $min
28
     * @param int|null $max
29
     * @param bool $no_remainders
30
     * @param bool $preserve_keys
31
     * @return array
32
     */
33
    public function arrayChunks($min = 0, $max = null, $no_remainders = false, $preserve_keys = true): array
34
    {
35
        $chunks = array_chunk(
36
            $this->array,
37
            (new ChunkSizer(count($this->array), $min, $max))->execute(),
38
            $preserve_keys
39
        );
40
41
        // Check if the first chunk is the same length as the last chunk
42
        if ($no_remainders && count($chunks[0]) != count(array_reverse($chunks)[0])) {
43
            $remainder = array_pop($chunks);
44
            $last_chunk = array_pop($chunks);
45
46
            // Add the remainder chunk to the last equal sized chunk
47
            $chunks[] = array_merge($last_chunk, $remainder);
48
        }
49
50
        return $chunks;
51
    }
52
53
    /**
54
     * Flatten a multidimensional array into a 2D array without nested keys.
55
     *
56
     * @param bool $nest_keys
57
     * @return array
58
     */
59
    public function arrayFlattenKeys($nest_keys = true): array
60
    {
61
        $flat = [];
62
        foreach (array_keys($this->array) as $key) {
63
            if (is_array($this->array[$key])) {
64
                // If the key is an array, add each children keys to flattened array
65
                foreach ($this->array[$key] as $k => $v) {
66
                    if ($nest_keys) {
67
                        $flat[$key.'_'.$k] = $v;
68
                    } else {
69
                        $flat[$k] = $v;
70
                    }
71
                }
72
            } else {
73
                $flat[$key] = $this->array[$key];
74
            }
75
        }
76
77
        return $flat;
78
    }
79
80
    /**
81
     * Remove particular keys from a multidimensional array.
82
     *
83
     * @param array|string $keys
84
     * @return array
85
     */
86
    public function arrayRemoveKeys($keys): array
87
    {
88
        $all_keys = array_keys($this->array);
89
        foreach ((array) $keys as $key) {
90
            if (in_array($key, $all_keys)) {
91
                unset($this->array[$key]);
92
            }
93
        }
94
95
        return $this->array;
96
    }
97
98
    /**
99
     * Sum the values of two arrays.
100
     *
101
     * @param array $array2
102
     * @return array
103
     */
104
    public function sumArrays(array $array2): array
105
    {
106
        // todo: add ability to pass array of arrays
107
        $array = [];
108
        foreach ($this->array as $index => $value) {
109
            $array[$index] = isset($array2[$index]) ? $array2[$index] + $value : $value;
110
        }
111
112
        return $array;
113
    }
114
115
    /**
116
     * Determine if all values in an array of key => value pairs are unique.
117
     *
118
     * @return bool
119
     */
120
    public function arrayValuesUnique(): bool
121
    {
122
        try {
123
            // Count the number of unique array values
124
            // Check to see if there is more than unique array_value
125
            return count(array_unique(array_values($this->array))) >= count(array_values($this->array));
126
        }
127
128
        // Handle nested arrays by comparing number unique keys
129
        catch (\ErrorException $exception) {
130
            $values = [];
131
            $valueCount = 0;
132
            foreach (array_values($this->array) as $value) {
133
                $values = array_merge($values, $value);
134
                $valueCount += count($value);
135
            }
136
137
            return count($values) == $valueCount;
138
        }
139
    }
140
141
    /**
142
     * Determine if all array_values are equal to a certain value.
143
     *
144
     * @param mixed $value
145
     * @return bool
146
     */
147
    public function arrayValuesEqual($value): bool
148
    {
149
        // Check if all array values are equal to a certain value
150
        return count(array_keys($this->array, $value)) == count($this->array);
151
    }
152
153
    /**
154
     * Determine if an array is multidimensional and has keys.
155
     *
156
     * @return bool
157
     */
158
    public function arrayHasKeys(): bool
159
    {
160
        // Array doesn't have keys if the array is the same as the array values
161
        if ($this->array == array_values($this->array)) {
162
            return false;
163
        }
164
165
        return count($this->array) == count($this->array, COUNT_RECURSIVE);
166
    }
167
168
    /**
169
     * Remove specific arrays of keys without modifying the original array.
170
     *
171
     * @param array $except
172
     * @return array
173
     */
174
    public function array_except(array $except): array
175
    {
176
        return array_diff_key($this->array, array_flip((array) $except));
177
    }
178
179
    /**
180
     * Remove a key from an array & return the key's value.
181
     *
182
     * @param string $key
183
     * @return mixed
184
     */
185
    public function arrayPop(string $key)
186
    {
187
        // Get the value
188
        $value = $this->array[$key];
189
190
        // Remove the value from the array
191
        unset($this->array[$key]);
192
193
        // Return the value
194
        return $value;
195
    }
196
197
    /**
198
     * Remove a key from an array & the new array without the key.
199
     *
200
     * @param array|string $keys
201
     * @return array
202
     */
203
    public function arrayUnset($keys): array
204
    {
205
        // Remove the values from the array
206
        foreach ((array) $keys as $key) {
207
            unset($this->array[$key]);
208
        }
209
210
        // Return the new array
211
        return $this->array;
212
    }
213
214
    /**
215
     * Determine if all values in an array are null.
216
     *
217
     * @return bool
218
     */
219
    public function arrayValuesNull(): bool
220
    {
221
        return $this->arrayValuesEqual(null);
222
    }
223
224
    /**
225
     * Retrieve a random array of elements.
226
     *
227
     * @param int $items
228
     * @return array
229
     */
230
    public function random(int $items): array
231
    {
232
        $keys = array_rand($this->array, $items);
233
234
        return array_filter($this->array, function ($value, $key) use ($keys) {
235
            return in_array($key, $keys);
0 ignored issues
show
Bug introduced by
It seems like $keys can also be of type integer and string; however, parameter $haystack of in_array() does only seem to accept array, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

235
            return in_array($key, /** @scrutinizer ignore-type */ $keys);
Loading history...
236
        }, ARRAY_FILTER_USE_BOTH);
237
    }
238
}
239