Completed
Push — master ( 563ab4...502bce )
by Hong
01:48
created

PriorityQueueTrait::getIterator()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 5

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 5
c 0
b 0
f 0
rs 10
cc 1
nc 1
nop 0
1
<?php
2
3
/**
4
 * Phoole (PHP7.2+)
5
 *
6
 * @category  Library
7
 * @package   Phoole\Base
8
 * @copyright Copyright (c) 2019 Hong Zhang
9
 */
10
declare(strict_types=1);
11
12
namespace Phoole\Base\Queue;
13
14
/**
15
 * PriorityQueueTrait
16
 *
17
 * @package Phoole\Base
18
 */
19
trait PriorityQueueTrait
20
{
21
    /**
22
     * data storage
23
     *
24
     * @var  array
25
     */
26
    protected $queue = [];
27
28
    /**
29
     * marker for sorted or not
30
     *
31
     * @var  bool
32
     */
33
    protected $sorted = true;
34
35
    /**
36
     * counter for priority
37
     *
38
     * @var  int
39
     */
40
    protected $counter = 20000000;
41
42
    /**
43
     * {@inheritDoc}
44
     */
45
    public function insert($data, int $priority = 0): void
46
    {
47
        $i = $this->getIndex($priority);
48
        $this->queue[$i] = ['data' => $data, 'priority' => $priority];
49
        $this->sorted = false;
50
    }
51
52
    /**
53
     * {@inheritDoc}
54
     */
55
    public function combine(PriorityQueueInterface $queue): PriorityQueueInterface
56
    {
57
        $nqueue = clone $this;
58
        foreach ($queue->queue as $data) {
0 ignored issues
show
Bug introduced by
Accessing queue on the interface Phoole\Base\Queue\PriorityQueueInterface suggest that you code against a concrete implementation. How about adding an instanceof check?

If you access a property on an interface, you most likely code against a concrete implementation of the interface.

Available Fixes

  1. Adding an additional type check:

    interface SomeInterface { }
    class SomeClass implements SomeInterface {
        public $a;
    }
    
    function someFunction(SomeInterface $object) {
        if ($object instanceof SomeClass) {
            $a = $object->a;
        }
    }
    
  2. Changing the type hint:

    interface SomeInterface { }
    class SomeClass implements SomeInterface {
        public $a;
    }
    
    function someFunction(SomeClass $object) {
        $a = $object->a;
    }
    
Loading history...
59
            $nqueue->insert($data['data'], $data['priority']);
60
        }
61
        return $nqueue;
62
    }
63
64
    /**
65
     * {@inheritDoc}
66
     */
67
    public function count()
68
    {
69
        return count($this->queue);
70
    }
71
72
    /**
73
     * {@inheritDoc}
74
     */
75
    public function getIterator()
76
    {
77
        $this->sortQueue();
78
        return new \ArrayIterator(array_column($this->queue, 'data'));
79
    }
80
81
    /**
82
     * Generate an integer key
83
     *
84
     * @param  int $priority
85
     * @throws \RuntimeException  priority out of range
86
     * @return int
87
     */
88
    protected function getIndex(int $priority): int
89
    {
90
        if (abs($priority) > 1000) {
91
            throw new \RuntimeException("Priority $priority out of range.");
92
        }
93
        return --$this->counter + $priority * 10000;
94
    }
95
96
    /**
97
     * Sort the queue from higher to lower int $key
98
     *
99
     * @return $this
100
     */
101
    protected function sortQueue()
102
    {
103
        if (!$this->sorted) {
104
            krsort($this->queue);
105
            $this->sorted = true;
106
        }
107
        return $this;
108
    }
109
}
110