Differences Between: [Versions 311 and 400] [Versions 311 and 401] [Versions 311 and 402] [Versions 311 and 403]
1 <?php 2 // This file is part of Moodle - http://moodle.org/ 3 // 4 // Moodle is free software: you can redistribute it and/or modify 5 // it under the terms of the GNU General Public License as published by 6 // the Free Software Foundation, either version 3 of the License, or 7 // (at your option) any later version. 8 // 9 // Moodle is distributed in the hope that it will be useful, 10 // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 // GNU General Public License for more details. 13 // 14 // You should have received a copy of the GNU General Public License 15 // along with Moodle. If not, see <http://www.gnu.org/licenses/>. 16 17 /** 18 * Question statistics calculations class. Used in the quiz statistics report. 19 * 20 * @package core_question 21 * @copyright 2018 Ryan Wyllie <ryan@moodle.com> 22 * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later 23 */ 24 25 namespace core_question\statistics\questions; 26 defined('MOODLE_INTERNAL') || die(); 27 28 /** 29 * Class calculated_question_summary 30 * 31 * This class is used to indicate the statistics for a random question slot should 32 * be rendered with a link to a summary of the displayed questions. 33 * 34 * It's used in the limited view of the statistics calculation in lieu of adding 35 * the stats for each subquestion individually. 36 * 37 * @copyright 2018 Ryan Wyllie <ryan@moodle.com> 38 * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later 39 */ 40 class calculated_question_summary extends calculated { 41 42 /** 43 * @var int only set immediately before display in the table. The order of display in the table. 44 */ 45 public $subqdisplayorder; 46 47 /** 48 * @var calculated[] The instances storing the calculated stats of the questions that are being summarised. 49 */ 50 protected $subqstats; 51 52 /** 53 * calculated_question_summary constructor. 54 * 55 * @param \stdClass $question 56 * @param int $slot 57 * @param calculated[] $subqstats The instances of the calculated stats of the questions that are being summarised. 58 */ 59 public function __construct($question, $slot, $subqstats) { 60 parent::__construct($question, $slot); 61 62 $this->subqstats = $subqstats; 63 $this->subquestions = implode(',', array_column($subqstats, 'questionid')); 64 } 65 66 /** 67 * This is a summary stat so never breakdown by variant. 68 * 69 * @return bool 70 */ 71 public function break_down_by_variant() { 72 return false; 73 } 74 75 /** 76 * Returns the minimum and maximum values of the given attribute in the summarised calculated stats. 77 * 78 * @param string $attribute The attribute that we are looking for its extremums. 79 * @return array An array of [min,max] 80 */ 81 public function get_min_max_of($attribute) { 82 $getmethod = 'get_min_max_of_' . $attribute; 83 if (method_exists($this, $getmethod)) { 84 return $this->$getmethod(); 85 } else { 86 $min = $max = null; 87 $set = false; 88 89 // We cannot simply use min or max functions because, in theory, some attributes might be non-scalar. 90 foreach (array_column($this->subqstats, $attribute) as $value) { 91 if (is_scalar($value) || is_null($value)) { 92 if (!$set) { // It is not good enough to check if (!isset($min)), 93 // because $min might have been set to null in an earlier iteration. 94 $min = $value; 95 $max = $value; 96 $set = true; 97 } 98 99 $min = $this->min($min, $value); 100 $max = $this->max($max, $value); 101 } 102 } 103 104 return [$min, $max]; 105 } 106 } 107 108 /** 109 * Returns the minimum and maximum values of the standard deviation in the summarised calculated stats. 110 * @return array An array of [min,max] 111 */ 112 protected function get_min_max_of_sd() { 113 $min = $max = null; 114 $set = false; 115 116 foreach ($this->subqstats as $subqstat) { 117 if (isset($subqstat->sd) && $subqstat->maxmark) { 118 $value = $subqstat->sd / $subqstat->maxmark; 119 } else { 120 $value = null; 121 } 122 123 if (!$set) { // It is not good enough to check if (!isset($min)), 124 // because $min might have been set to null in an earlier iteration. 125 $min = $value; 126 $max = $value; 127 $set = true; 128 } 129 130 $min = $this->min($min, $value); 131 $max = $this->max($max, $value); 132 } 133 134 return [$min, $max]; 135 } 136 137 /** 138 * Find higher value. 139 * A zero value is almost considered equal to zero in comparisons. The only difference is that when being compared to zero, 140 * zero is higher than null. 141 * 142 * @param float|null $value1 143 * @param float|null $value2 144 * @return float|null 145 */ 146 protected function max(float $value1 = null, float $value2 = null) { 147 $temp1 = $value1 ?: 0; 148 $temp2 = $value2 ?: 0; 149 150 $tempmax = max($temp1, $temp2); 151 152 if (!$tempmax && $value1 !== 0 && $value2 !== 0) { 153 $max = null; 154 } else { 155 $max = $tempmax; 156 } 157 158 return $max; 159 } 160 161 /** 162 * Find lower value. 163 * A zero value is almost considered equal to zero in comparisons. The only difference is that when being compared to zero, 164 * zero is lower than null. 165 * 166 * @param float|null $value1 167 * @param float|null $value2 168 * @return mixed|null 169 */ 170 protected function min(float $value1 = null, float $value2 = null) { 171 $temp1 = $value1 ?: 0; 172 $temp2 = $value2 ?: 0; 173 174 $tempmin = min($temp1, $temp2); 175 176 if (!$tempmin && $value1 !== 0 && $value2 !== 0) { 177 $min = null; 178 } else { 179 $min = $tempmin; 180 } 181 182 return $min; 183 } 184 }
title
Description
Body
title
Description
Body
title
Description
Body
title
Body