Test Failed
Push — develop ( f741b1...4c7784 )
by Alec
05:40
created

Timer::computeAverage()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 2
CRAP Score 1

Importance

Changes 0
Metric Value
cc 1
eloc 1
nc 1
nop 0
dl 0
loc 3
ccs 2
cts 2
cp 1
crap 1
rs 10
c 0
b 0
f 0
1
<?php
2
3
namespace AlecRabbit\Tools;
4
5
use AlecRabbit\Pretty;
6
use AlecRabbit\Tools\Contracts\TimerInterface;
7
use AlecRabbit\Tools\Reports\Contracts\ReportableInterface;
8
use AlecRabbit\Tools\Reports\Traits\Reportable;
9
use AlecRabbit\Tools\Traits\TimerFields;
10
11
class Timer implements TimerInterface, ReportableInterface
12
{
13
    use TimerFields, Reportable;
14
15
    /**
16
     * Timer constructor.
17
     * @param null|string $name
18
     * @param bool $start
19 20
     */
20
    public function __construct(?string $name = null, bool $start = true)
21 20
    {
22 20
        $this->name = $this->defaultName($name);
23 20
        $this->creation = $this->current();
24
        if ($start) {
25
            $this->start($this->creation);
26
        }
27
    }
28 20
29
    /**
30
     * @return float
31 20
     */
32
    public function current(): float
33
    {
34
        return
35
            microtime(true);
36
    }
37 10
38
    /**
39 10
     * Starts the timer.
40 8
     *
41 8
     * @param null|float $point
42
     * @return void
43 10
     */
44 10
    public function start(?float $point = null): void
45
    {
46
        $this->previous = $point ?? $this->current();
47
        $this->started = true;
48
    }
49
50
    /**
51 12
     * {@inheritdoc}
52
     */
53 12
    public function prepareForReport(): void
54 12
    {
55 12
        if ($this->isNotStarted()) {
56
            $this->start();
57
            $this->mark();
58
        }
59
        $this->stop();
60 11
    }
61
62 11
    /**
63 11
     * @param int|null $iterationNumber
64 11
     */
65
    private function mark(?int $iterationNumber = null): void
66 11
    {
67 4
        $current = $this->current();
68 4
        $this->currentValue = $current - $this->previous;
69 1
        $this->previous = $current;
70 1
71
        $this->compute($iterationNumber);
72 4
    }
73 1
74 1
    /**
75
     * @param null|int $iterationNumber
76 4
     */
77
    private function compute(?int $iterationNumber): void
78 11
    {
79 11
        if (0 !== $this->count) {
80 11
            ++$this->count;
81 11
            $this->checkMinValue($iterationNumber);
82
            $this->checkMaxValue($iterationNumber);
83 11
            $this->computeAverage();
84
        } else {
85 12
            $this->initValues();
86
        }
87 12
    }
88 12
89 12
    /**
90
     * @param null|int $iterationNumber
91
     */
92
    private function checkMinValue(?int $iterationNumber): void
93
    {
94
        if ($this->currentValue < $this->minValue) {
95
            $this->minValue = $this->currentValue;
96
            $this->minValueIteration = $iterationNumber ?? $this->count;
97 6
        }
98
    }
99 6
100 2
    /**
101
     * @param null|int $iterationNumber
102 6
     */
103
    private function checkMaxValue(?int $iterationNumber): void
104 6
    {
105
        if ($this->currentValue > $this->maxValue) {
106
            $this->maxValue = $this->currentValue;
107
            $this->maxValueIteration = $iterationNumber ?? $this->count;
108
        }
109
    }
110
111 5
    private function computeAverage(): void
112
    {
113 5
        $this->avgValue = (($this->avgValue * ($this->count - 1)) + $this->currentValue) / $this->count;
114 3
    }
115
116
    private function initValues(): void
117 5
    {
118
        $this->maxValueIteration = $this->minValueIteration = $this->count = 1;
119
        $this->maxValue = $this->currentValue;
120
        $this->minValue = $this->currentValue;
121
        $this->avgValue = $this->currentValue;
122
    }
123
124
    public function stop(): void
125
    {
126
        $this->computeElapsed();
127
        $this->stopped = true;
128
    }
129
130
    private function computeElapsed(): void
131
    {
132
        $this->elapsed = $this->current() - $this->creation;
133
    }
134
135
    /**
136
     * Marks the time.
137
     * If timer was not started starts the timer.
138
     * @param int|null $iterationNumber
139
     * @return Timer
140
     */
141
    public function check(?int $iterationNumber = null): Timer
142
    {
143
        if ($this->isNotStarted()) {
144
            $this->start();
145
        } else {
146
            $this->mark($iterationNumber);
147
        }
148
        return $this;
149
    }
150
151
    /**
152
     * @param float $start
153
     * @param float $stop
154
     * @param null|int $iterationNumber
155
     * @return Timer
156
     */
157
    public function bounds(float $start, float $stop, ?int $iterationNumber = null): Timer
158
    {
159
        if ($this->isNotStarted()) {
160
            $this->start();
161
        }
162
        $this->currentValue = $stop - $start;
163
        $this->previous = $stop;
164
165
        $this->compute($iterationNumber);
166
        return $this;
167
    }
168
169
    /**
170
     * @param bool $pretty
171
     * @return mixed
172
     */
173
    public function elapsed(bool $pretty = true)
174
    {
175
        if ($this->isNotStopped()) {
176
            $this->stop();
177
        }
178
        return
179
            $pretty ? Pretty::seconds($this->getElapsed()) : $this->elapsed;
180
    }
181
182
    /**
183
     * @return float
184
     */
185
    public function getElapsed(): float
186
    {
187
        if ($this->isNotStopped()) {
188
            $this->computeElapsed();
189
        }
190
        return $this->elapsed;
191
    }
192
}
193