不确定如何为测验程序构建代码。

时间:2014-05-21 20:30:34

标签: c

在过去的3天里,我已经为家庭作业写了+删除+书面+已删除的代码,我在智慧结束时。这是我第一次被这个学期难倒,而且我开始有点疯狂了。

基本理念:

创建通用多项选择测验程序

问题将存储在结构中的文本文件中,如下所示:

  • 问题

  • 选择次数

  • 选择本身(每个都在新行上)

  • 正确答案

一切都很好,但是让我疯狂的是,每个问题的选择数量各不相同,而且它们都在同一个文件中。

有人可以看看我到目前为止的代码,并给我一些指导。 这是家庭作业,我不想要答案,只是一些帮助!

代码

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

typedef struct _question {
char question[50];
int numChoices;
int numChoicesLine;
char choices[100][100];
char correctAns[50];
} Question;


void getQuestion (FILE file, int *firstLine) {

// init struct
Question q;

// array to store lines in the file
char lines[100][100];

int i = 0; // counter

// read all lines into lines array
while(fgets(lines[i], 100, &file))
{
// keep track of how many lines there are in the file
++i;
}

// i want j to reference the first line of each new question set
int j = *firstLine;

// get the question
strcpy(q.question, lines[j]);
printf("%s", q.question);

// get number of choices
for (int j = *firstLine; j < i; ++j)
{
// if the line is a number store that number into numChoices and which line of the file
// the number is found

if(atoi(lines[j]))

{
q.numChoices = atoi(lines[j]);
q.numChoicesLine = j;
break;
}
}

// store choices in array lines[k]
int k = 0;
for (k = q.numChoicesLine+1; k <= q.numChoices + 1; ++k)
{
// loop from the first choice to the last choice

fgets(lines[k], 100, &file);
strcpy(q.choices[k],lines[k]);
printf("-%s", q.choices[k]);
}

// store correct ans
// after the above loop, k refers to the line of the last choice in the quiz
strcpy(q.correctAns, lines[k]);

// set the firstLine to the line that stores the question for the next set
*firstLine = k + 1;
}


int main()
{
// open file
FILE *files;
files = fopen("tickle.txt", "r");
int firstLine = 0; // the first time it will be 0
getQuestion(*files, &firstLine);
return 0;
}

数据文件的示例:

  

谁是美国总统?

     

3

     

乔治布什

     迈克尔乔丹

     巴拉克奥巴马

     巴拉克奥巴马

     

墨西哥北部的哪个国家?

     

2

     

USA

     

加拿大

     

USA

3 个答案:

答案 0 :(得分:2)

以下是一些有用的观点:

将getQuestion函数分解为几个较小的函数。尝试以准确表示函数功能的方式命名每个函数。

想想你可以写一次并重复使用的 helper / utility 函数。

考虑如何使代码更清晰,更易于阅读,理解,修改和维护。

代码如下:

void GetQuestion ()
{
   DoStep1();
   DoStep2();
   DoStep3();
}

void DoStep1()
{
   DoStep1A();
   DoStep1B();
   DoStep1C();
}

void DoStep2()
{
   DoStep2A();
   DoStep2B();
   DoStep2C();
}

void DoStep3()
{
   DoStep3A();
   DoStep3B();
   DoStep3C();
}

比这样的代码组织得更好:

void GetQuestion()
{ 
   ... // Step 1a
   ... // Step 1b
   ... // Step 1c
   ... // Step 2a
   ... // Step 2b
   ... // Step 2c
   ... // Step 3a
   ... // Step 3b
   ... // Step 3c
}

&#34; DoStep&#34;您的任何功能都可能不是一个好名字。我使用这些名称作为占位符,以便您可以弄清楚如何命名自己的函数。

答案 1 :(得分:1)

  • 使用scanf函数:它们被设计用于处理这类问题(逐行阅读,简单模式)。
  • 将文件记录规范转换为scanf指令,不要忘记检查调用结果(查看函数的man page以获取更多信息)。
  • 不要将所有文件一次性加载到一个数组中,直接逐行处理它会容易得多。
  • 对于您的Question数据结构,您应该已经知道如何使用malloc(分配)和free(处置)动态管理内存。使用它来匹配答案的数量(我想它们的最大长度固定为100)
  • 正如LVBen所说,以有意义的单位分解你的代码。

答案 2 :(得分:0)

促使你疯狂的最大交易之一是:

for (k = q.numChoicesLine+1; k <= q.numChoices + 1; ++k)

实际上,您从q.numChoicesLine+1q.numChoicesLine+q.numChoices提取您的选择 让我们说你从第7行开始有3个选择,所以你需要使用for循环读取第7,8,9行:

for(i=7; i< 7+3; i++)

而不是

for(i=7; i<3; i++)

我的建议是像这样使用for循环:

for (k = q.numChoicesLine+1; k <= q.numChoicesLine+q.numChoices; ++k)

得到它?