]> git.mjollnir.org Git - moodle.git/commitdiff
MDL-15268 "Content for Quiz Statistics report table" know looping through all questio...
authorjamiesensei <jamiesensei>
Wed, 16 Jul 2008 11:55:38 +0000 (11:55 +0000)
committerjamiesensei <jamiesensei>
Wed, 16 Jul 2008 11:55:38 +0000 (11:55 +0000)
lang/en_utf8/quiz_statistics.php
mod/quiz/report/statistics/report.php
mod/quiz/report/statistics/statistics_table.php

index 1a5d13764cf5a577a8ad83b09a919c58c12c54eb..c51bef67a815ecebc450bcafedc78e22ba3872e9 100644 (file)
@@ -24,6 +24,7 @@ $string['attemptsfirst'] = 'first attempt';
 $string['errormedian'] = 'Error fetching median';
 $string['errorpowers'] = 'Error fetching data to calculate variance for quiz grades';
 $string['errorpowerquestions'] = 'Error fetching data to calculate variance for question grades';
+$string['errorstatisticsquestions'] = 'Error fetching data to calculate statistics for question grades';
 $string['median'] = 'Median grade';
 $string['standarddeviation'] = 'Standard deviation';
 $string['skewness'] = 'Score distribution skewness';
@@ -34,8 +35,11 @@ $string['standarderror'] = 'Standard error';
 $string['questionnumber'] = 'Q#';
 $string['quizstructureanalysis'] = 'Quiz structure analysis';
 $string['questiontype'] = 'Q type';
-$string['intended_weight'] = 'Intended question weight';
+$string['intended_weight'] = 'Intended weight';
 $string['random_guess_score'] = 'Random guess score';
 $string['facility'] = 'Facility index';
 $string['nostudentsingroup'] = 'There are no students in this group yet';
+$string['discrimination_index'] = 'Discrimination Index';
+$string['discriminative_efficiency'] = 'Discriminative Efficiency';
+$string['effective_weight'] = 'Effective weight';
 ?>
\ No newline at end of file
index b782dc070b00ff782b96b19626391cd7143873c7..9e4c2659c4573a1b06b80f42a7c262976a59b9b4 100644 (file)
@@ -144,6 +144,7 @@ class quiz_statistics_report extends quiz_default_report {
                 }
                 $usingattempts->heading = get_string('statsfor', 'quiz_statistics', $usingattempts->attempts);
                 $s = $usingattempts->countrecs;
+                $sumgradesavg = $usingattempts->total / $usingattempts->countrecs;
             }
         } else {
             $s = 0;
@@ -243,11 +244,14 @@ class quiz_statistics_report extends quiz_default_report {
             }
         }
         if ($s){
-            //CIC, ER and SE.
+/*            //CIC, ER and SE.
             //http://docs.moodle.org/en/Development:Quiz_item_analysis_calculations_in_practise#CIC.2C_ER_and_SE
             list($qsql, $sqlparams) = $DB->get_in_or_equal(array_keys($questions), SQL_PARAMS_NAMED);
             $sqlparams += $qaparams;//put quiz id in at beginning of array
-            $qgradeavgsql = "SELECT qs.question, AVG(qs.grade) FROM " .
+            $qgradeavgsql = "SELECT qs.question, " .
+                    "AVG(qs.grade) AS gradeaverage " .
+                    "AVG(qa.sumgrades - qs.grade) AS sumgradeaverage " .
+                    "FROM " .
                     "{question_sessions} qns, " .
                     "{question_states} qs, " .
                     $fromqa.' '.
@@ -256,7 +260,7 @@ class quiz_statistics_report extends quiz_default_report {
                     'AND qs.question '.$qsql.' ' .
                     $usingattempts->sql.
                     'AND qns.newgraded = qs.id GROUP BY qs.question';
-            $qgradeavgs = $DB->get_records_sql_menu($qgradeavgsql, $sqlparams);
+            $qgradeavgs = $DB->get_records_sql($qgradeavgsql, $sqlparams);
             
             $sum = 0;
             $sql = 'SELECT COUNT(1) as s,' .
@@ -283,13 +287,112 @@ class quiz_statistics_report extends quiz_default_report {
                 }
                 $sum += $fromdb->power2;
             }
+            //Discrimination index
+            $sql = 'SELECT qs.id, ' .
+                    'qs.question, ' .
+                    'qa.sumgrades - qs.grade AS sum, ' .
+                    'qs.grade ' .
+                    'FROM ' .
+                    '{question_sessions} qns, ' .
+                    '{question_states} qs, '.
+                    $fromqa.' '.
+                    'WHERE ' .$whereqa.
+                    'AND qns.attemptid = qa.uniqueid '.
+                    $usingattempts->sql.
+                    'AND qns.newgraded = qs.id';
+            $fromdbrs = $DB->get_recordset_sql($sql, $qaparams);
+            if ($fromdbrs === false){
+                print_error('errorpowerquestions', 'quiz_statistics');
+            }
+            foreach ($fromdbrs as $record){
+                
+            }*/
+            $sql = 'SELECT qs.id, ' .
+                    'qs.question, ' .
+                    'qa.sumgrades, ' .
+                    'qs.grade ' .
+                    'FROM ' .
+                    '{question_sessions} qns, ' .
+                    '{question_states} qs, '.
+                    $fromqa.' '.
+                    'WHERE ' .$whereqa.
+                    'AND qns.attemptid = qa.uniqueid '.
+                    $usingattempts->sql.
+                    'AND qns.newgraded = qs.id';
+            $fromdbrs = $DB->get_recordset_sql($sql, $qaparams);
+            if ($fromdbrs === false){
+                print_error('errorstatisticsquestions', 'quiz_statistics');
+            }
+            foreach (array_keys($questions) as $qid){
+                $questions[$qid]->s = 0;
+                $questions[$qid]->totalgrades = 0;
+                $questions[$qid]->totalothergrades = 0;
+                $questions[$qid]->gradevariancesum = 0;
+                $questions[$qid]->othergradevariancesum = 0;
+                $questions[$qid]->covariancesum = 0;
+                $questions[$qid]->covariancemaxsum = 0;
+                $questions[$qid]->covariancewithoverallgradesum = 0;
+                $questions[$qid]->gradearray = array();
+                $questions[$qid]->othergradesarray = array();
+            }
+            
+            foreach ($fromdbrs as $record){
+                $questions[$record->question]->s++;
+                $questions[$record->question]->totalgrades += $record->grade;
+                $questions[$record->question]->totalothergrades += $record->sumgrades - $record->grade;
+                //need to sort these to calculate max covariance :
+                $questions[$record->question]->gradearray[] = $record->grade;
+                $questions[$record->question]->othergradesarray[] = $record->sumgrades - $record->grade;
+            }
+            foreach (array_keys($questions) as $qid){
+                $questions[$qid]->gradeaverage = $questions[$qid]->totalgrades / $s;
+                $questions[$qid]->facility = $questions[$qid]->gradeaverage / $questions[$qid]->grade;
+                $questions[$qid]->othergradeaverage = $questions[$qid]->totalothergrades / $s;
+                sort($questions[$qid]->gradearray, SORT_NUMERIC);
+                sort($questions[$qid]->othergradesarray, SORT_NUMERIC);
+            }
+            //go through the records one more time
+            foreach ($fromdbrs as $record){
+                $gradedifference = ($record->grade - $questions[$record->question]->gradeaverage);
+                $othergradedifference = (($record->sumgrades - $record->grade) - $questions[$record->question]->othergradeaverage);
+                $overallgradedifference = $record->sumgrades - $sumgradesavg;
+                $sortedgradedifference = (array_shift($questions[$qid]->gradearray) - $questions[$record->question]->gradeaverage);
+                $sortedothergradedifference = (array_shift($questions[$qid]->othergradesarray) - $questions[$record->question]->othergradeaverage);
+                $questions[$record->question]->gradevariancesum += pow($gradedifference,2);
+                $questions[$record->question]->othergradevariancesum += pow($othergradedifference,2);
+                $questions[$record->question]->covariancesum += $gradedifference * $othergradedifference;
+                $questions[$record->question]->covariancemaxsum += $sortedgradedifference * $sortedothergradedifference;
+                $questions[$record->question]->covariancewithoverallgradesum += $gradedifference * $overallgradedifference;
+            }
+            $sumofcovariancewithoverallgrade = 0;
+            $sumofgradevariance =0;
+            foreach (array_keys($questions) as $qid){
+                $questions[$qid]->gradevariance = $questions[$qid]->gradevariancesum / ($s -1);
+                $questions[$qid]->othergradevariance = $questions[$qid]->othergradevariancesum / ($s -1);
+                $questions[$qid]->covariance = $questions[$qid]->covariancesum / ($s -1);
+                $questions[$qid]->covariancemax = $questions[$qid]->covariancemaxsum / ($s -1);
+                $sumofgradevariance += $questions[$qid]->gradevariance;
+                $questions[$qid]->covariancewithoverallgrade = $questions[$qid]->covariancewithoverallgradesum / ($s-1);
+                $sumofcovariancewithoverallgrade += sqrt($questions[$qid]->covariancewithoverallgrade);
+                $questions[$qid]->sd = sqrt($questions[$qid]->gradevariancesum / ($s -1));
+                //avoid divide by zero
+                if (sqrt($questions[$qid]->gradevariance * $questions[$qid]->othergradevariance)){
+                    $questions[$qid]->discriminationindex = 100*$questions[$qid]->covariance 
+                                / sqrt($questions[$qid]->gradevariance * $questions[$qid]->othergradevariance);
+                } else {
+                    $questions[$qid]->discriminationindex = '';
+                }
+                $questions[$qid]->discriminativeefficiency = 100*$questions[$qid]->covariance / $questions[$qid]->covariancemax;
+            }
+            foreach (array_keys($questions) as $qid){
+                $questions[$qid]->effectiveweight = 100 * sqrt($questions[$qid]->covariancewithoverallgrade)/$sumofcovariancewithoverallgrade;
+            }
         }
         if (!$table->is_downloading()){
             if ($s>1){
-                $sumofvarianceforallpositions = $sum / ($s -1);
-                $p = count($qgradeavgs);//no of positions
+                $p = count($questions);//no of positions
                 if ($p > 1){
-                    $cic = (100 * $p / ($p -1)) * (1 - ($sumofvarianceforallpositions/$k2));
+                    $cic = (100 * $p / ($p -1)) * (1 - ($sumofgradevariance)/$k2);
                     $quizattsstatistics->data[] = array(get_string('cic', 'quiz_statistics'), number_format($cic, $quiz->decimalpoints).' %');
                     $errorratio = 100 * sqrt(1-($cic/100));
                     $quizattsstatistics->data[] = array(get_string('errorratio', 'quiz_statistics'), number_format($errorratio, $quiz->decimalpoints).' %');
index 6de8aef07fd37e79b29b9b3daff4176c05bd39ea..ebf425363ff7d8d8718947c6f7833e00b81c57f2 100644 (file)
@@ -51,6 +51,15 @@ class quiz_report_statistics_table extends flexible_table {
         $columns[]= 'intended_weight';
         $headers[]= get_string('intended_weight', 'quiz_statistics');
         
+        $columns[]= 'effective_weight';
+        $headers[]= get_string('effective_weight', 'quiz_statistics');
+        
+        $columns[]= 'discrimination_index';
+        $headers[]= get_string('discrimination_index', 'quiz_statistics');
+        
+        $columns[]= 'discriminative_efficiency';
+        $headers[]= get_string('discriminative_efficiency', 'quiz_statistics');
+        
         $this->define_columns($columns);
         $this->define_headers($headers);
         $this->sortable(false);
@@ -58,8 +67,11 @@ class quiz_report_statistics_table extends flexible_table {
         $this->column_class('s', 'numcol');
         $this->column_class('random_guess_score', 'numcol');
         $this->column_class('intended_weight', 'numcol');
+        $this->column_class('effective_weight', 'numcol');
         $this->column_class('sd', 'numcol');
         $this->column_class('facility', 'numcol');
+        $this->column_class('discrimination_index', 'numcol');
+        $this->column_class('discriminative_efficiency', 'numcol');
 
         // Set up the table
         $this->define_baseurl($reporturl->out());
@@ -107,7 +119,19 @@ class quiz_report_statistics_table extends flexible_table {
     function col_intended_weight($question){
         return quiz_report_scale_sumgrades_as_percentage($question->grade, $this->quiz);
     }
-
+    function col_effective_weight($question){
+        return number_format($question->effectiveweight, 2).' %';
+    }
+    function col_discrimination_index($question){
+        if (is_numeric($question->discriminationindex)){
+            return number_format($question->discriminationindex, 2).' %';
+        } else {
+            return $question->discriminationindex;
+        }
+    }
+    function col_discriminative_efficiency($question){
+        return number_format($question->discriminativeefficiency, 2).' %';
+    }
     function col_random_guess_score($question){
         $randomguessscore = question_get_random_guess_score($question);
         if (is_numeric($randomguessscore)){