As in the cycle to consider questions which had no answer?

Good day!

Code:
$answer = [
 1 => [2,3,4,5,52],
 2 => [7,8,9,52],
 3 => [10,11,12,25],
];

 $bd = [
[
 'id' => 2,
 'id_question' => 1,
 'correct_answer' => 1,
],
[
 'id' => 3,
 'id_question' => 1,
 'correct_answer' => 1,
],
[
 'id' => 4,
 'id_question' => 1,
 'correct_answer' => 1,
],
[
 'id' => 5,
 'id_question' => 1,
 'correct_answer' => 1,
],


[
 'id' => 7,
 'id_question' => 2,
 'correct_answer' => 1,
],
[
 'id' => 8,
 'id_question' => 2,
 'correct_answer' => 1,
],
[
 'id' => 9,
 'id_question' => 2,
 'correct_answer' => 1,
],


[
 'id' => 10,
 'id_question' => 3,
 'correct_answer' => 1,
],
[
 'id' => 11,
 'id_question' => 3,
 'correct_answer' => 1,
],
[
 'id' => 12,
 'id_question' => 3,
 'correct_answer' => 1,
],

[
 'id' => 13,
 'id_question' => 4,
 'correct_answer' => 1,
],
[
 'id' => 14,
 'id_question' => 4,
 'correct_answer' => 1,
],
[
 'id' => 15,
 'id_question' => 4,
 'correct_answer' => 1,
],
];


 $quests = [];
 foreach ($bd as $bd_element) {
 $quests[$bd_element['id_question']][] = $bd_element['id'];
}


 $a = 0;
 foreach ($quests as $id_quest => $ans) {
 $is = true;
 echo '<br><br>Question: No.'.$id_quest.'<br>';

 foreach ($ans as $an) {
 if (array_search($an, $answer[$id_quest]) === false) $is = false;
 echo 'Correct answers: '.$an.'<br>';
}

 foreach ($answer[$id_quest] as $answer_give) {
 if (array_search($answer_give, $ans) === false) $is = false;
 echo 'answer: '.$answer_give.'<br>';
}

 if ($is) $a++;
}

 echo '<br><br>Correct answers: '.$a.'<br>';


Processing answers to the questions. The question can be several answers.
Code needs:
- take into account only correct answers
- if not selected all the correct answers - the answer is not counted
- if selected for correct and incorrect answers - response to be counted
- if the answer to the question was not - the answer is not to be counted.

The above code will work for all items, except for accounting questions that had no answers.
I.e. in the example there are 4 a question that had no answer, but the cycle considers it as correct.
I can't find where to fix it.

Thanks in advance!
April 19th 20 at 12:35
1 answer
April 19th 20 at 12:37
Solution
$allAnswers = [
 1 => [2,3,4,5], // true, maybe the only correct answer
 2 => [7,8,9,52], // not correct, given incorrect 52
 3 => [10,11,12,25], // not correct, given an incorrect 25
 4 => [13], // not correct, maybe missing the correct answers are 14 and 15
];
$dbAnswers = [
 // data from DB
];

/** 
 * Groups of any array by any field $indexKey to index, 
 * and $columnKey as grouped values
*/
function groupBy(array $input, string $indexKey, string $columnKey): array
{
 return array_reduce($input, function($res, $data) use ($indexKey, $columnKey){
 if (!isset($data[$indexKey], $data[$columnKey])) {
 return $res;
}

 $res[$data[$indexKey]][] = $data[$columnKey];

 return $res;
 }, []);
}

/** 
 * Mapping of the input answers with the correct answers for each question
*/
computeAnswersResult function(array $inputAnswers, array $questionsWithCorrectAnswers): array
{
 $result = [];
 foreach($inputAnswers as $questIn => $answesrIn) {
 $correctAnswers = $questionsWithCorrectAnswers[$questIn] ?? [];

 $errors = array_diff($answesrIn, $correctAnswers);
 $corrects = array_diff($answesrIn, $errors); // if you didn't have to withdraw, then the code would be greatly reduced
 $correctDiff = array_diff($correctAnswers, $corrects);

 // If there are additional responses and number of correct answers entered 
 // the same as the number correct in the database, the status is positive
 $completed = \count($errors) === 0 && \count($correctDiff) === 0;

 $result[$questIn] = [
 'errors' => $errors,
 'corrects' => $corrects,
 'completed' => $completed,
];
}

 return $result;
}

// Include the correct answer for each question
$questionsWithCorrectAnswers = groupBy($dbAnswers, 'id_question', 'id');
// Mapim entered the answers on the right and get the result
$result = computeAnswersResult($allAnswers, $questionsWithCorrectAnswers);
// Count successful
$completedCount = \count(
 array_filter($result, function($answer) {
 return $answer['completed'] ?? false;
})
);

// DISPLAY 
$html = ";
foreach ($result as $questId => $details) {
 $status = $details['completed'] ? 'true' : 'not true';

 $html .= 'Question number:' . $questId . PHP_EOL;
 $html .= 'Correct answers:' . implode(', ', $details['corrects']) . PHP_EOL;
 $html .= 'The result of the question' . $status . PHP_EOL;
 $html .= '-------------------' . PHP_EOL;
}
$html .= 'Of all the faithful:' . $completedCount;

echo $html;
@sheridan.Schowalt, thank You very much! - phoebe_Dicki commented on April 19th 20 at 12:40

Find more questions by tags PHP