Как случайным образом отобразить значения в массиве, учитывая, что каждое из этих значений имеет уникальное соответствующее значение? - PullRequest
0 голосов
/ 07 ноября 2011

Используя C, Как я случайно отображаю значения в массиве, учитывая, что каждое из этих значений имеет уникальное соответствующее значение без повторения какого-либо из этих отображаемых значений? Используя C, моя цель состоит в том, чтобы случайным образом отображать вопросы по одному за определенное количество итераций. Я создал массив, который содержит вопросы и их четыре возможных ответа. Я также создал массив, содержащий правильный ответ на каждый вопрос.

Большое спасибо ... Вы, ребята, очень помогли

#include <stdio.h>
#include <conio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#include <time.h> 

int random();
int l, qs[10];
int main ()
{
for (l=0;l<10;++l)
qs[l]=0;
srand(time(NULL));
char questions [] [50]  ={"aa \n\na)\n\nb)\n\nc)\n\nd)",\"bb   \n\na)\n\nb)\n\nc)\n\nd)", "cc \n\na)\n\nb)\n\nc)\n\nd)", \
"dd \n\na)\n\nb)\n\nc)\n\nd)", "ee \n\na)\n\nb)\n\nc)\n\nd)", \
"ff \n\na)\n\nb)\n\nc)\n\nd)", "gg \n\na)\n\nb)\n\nc)\n\nd)", \
"hh \n\na)\n\nb)\n\nc)\n\nd)", "ii \n\na)\n\nb)\n\nc)\n\nd)", \
"jj \n\na)\n\nb)\n\nc)\n\nd)"};
char answers [10] = {'a','b', 'b','d','c','b','d','b' ,'c', 'b'};
int i, j;
char ans;
int score = 0;
printf ("Read each question carefully and choose your best answer.");
for (i=1;i<6;i++)
{
j = random();
fflush(stdin);
clrscr();
printf ("\n %d %s \n\n", i, questions [j]);
printf ("\n Enter Answer: ");
do
{
ans = tolower(getchar());
}while ( (ans < 'a') || (ans > 'd'));
printf ("\nYou chose: %c ", ans);
if (ans == answers[j])
{score = score + 1;
printf ("\n\nCorrect. %d Mark/s", score);
}else{printf ("\n\nIncorrect. 0 Mark/s");}
printf("\n\nPress Enter for next question...");
getch ();
}
getch ();
return 0;
}
random ()
{
int k;
do
{k=rand()%10;
}while (qs[k]!=0);
qs[k]= 1;
return k;
}

Ответы [ 3 ]

1 голос
/ 07 ноября 2011

Прежде всего, я бы изменил способ организации данных. Прямо сейчас у вас есть три параллельных массива, один для вопросов, один для потенциальных ответов и один для правильных ответов.

Вместо этого я бы создал структуру для хранения всех данных для одного вопроса, что-то вроде этого:

struct qa { 
    char question[64];
    char answers[4][32];
    int correct_answer;
};

Тогда я бы создал массив структур qa, каждый из которых содержал бы все данные для одного вопроса и ответа:

qa questions[] = {
    { "what color is the sky?", { "red", "green", "blue", "yellow"}, 2},
    { "When is Christmas?", {"January", "July", "September", "December"}, 3},
    // ...
};

Оттуда у вас есть несколько вариантов. Если вы собираетесь задать все (или почти) все вопросы и, в первую очередь, хотите перетасовать заказ, вы можете использовать перетасовку Фишера-Йейтса, как предложил @Salvatore Previti.

Если вы задаете лишь небольшой процент вопросов в любой момент времени, это может быть довольно расточительным. В таком случае вы можете использовать (для одного примера) алгоритм выбора, изобретенный Робертом Флойдом, который я обсуждал в предыдущем ответе .

0 голосов
/ 07 ноября 2011

Не вызывайте srand в цикле for.Вызовите это один раз в начале вашей программы и пусть это будет.Крутой способ сделать то, что вы хотите, это перемешивание Фишера-Йейтса.Вы можете посмотреть его, если хотите его использовать.если нет, вот тривиальное решение:

1) Перед циклом создайте массив bool размером 10 (плохо назовите его usedArray) и установите для всех значение false.

2) дляполучить индекс вопроса, получить случайное число от 0 до 9 включительно (j = rand% 10; это хорошо), так что usedArray [j] равно false;затем установите для usedArray [j] значение true.Вы можете использовать цикл while или do-while для этого.

2) Теперь ваш вопрос - это вопросы [j], и соответствующий ответ - ответы [j]

3) при необходимости повторите

0 голосов
/ 07 ноября 2011

Вам нужен еще один список, чтобы отслеживать, какой предмет вы извлекли.

Возможное решение: перемешать входной массив. Смотри http://benpfaff.org/writings/clc/shuffle.html

Если вы не можете изменить входной массив, вы можете вместо этого использовать индексы, уровень косвенности. Это еще одно возможное решение.

1) Вы создаете целочисленный массив размером n.

2) Вы заполняете массив значениями от 0 до n-1 (включены).

3) Вы перемешиваете массив (ищите метод перемешивания для рандомизации массива), например, снова http://benpfaff.org/writings/clc/shuffle.html

4) Затем вы перебираете массив от 0 до n-1 (включительно), каждый элемент массива будет индексом в исходном массиве.

Готово.

Другое возможное решение - использовать связанный список.

1) Вы заполняете связанный список в случайном порядке (это довольно просто).

в псевдокоде, например

for (int i = 0; i < n; ++i)
{
    if (rand() & 1)
        insert_at_the_beginning();
    else
        insert_at_the_end();
}

2) Когда вам нужен новый элемент, вы извлекаете первый элемент из связанного списка.

Готово.

Вы также можете сохранить массив булевых значений, но в этом случае сложность алгоритма будет выше, первого метода будет достаточно.

...