#include<stdio.h>
#include<stdlib.h>
#include <time.h>
int N; //題目的數量
typedef struct text1 //將題目定義為結構體
{int num; //題號
char topic[50]; //題目
char a[10],b[10],c[10],d[10]; //ABCD四個選項
char rightanswer[2]; //正確答案
}TEXT;
void teacher(TEXT text[]); //教師系統
void writetofile(TEXT text[],int i); //資料塊寫檔案
void student(TEXT text[]); //學生系統
void readfromfile(int n); //資料塊讀檔案
void menu(); //主選單
void print();
void ent_a();
void ent_s();
FILE *fp;
void main()
{ TEXT text[100];
int a;
printf("\n\n\n\n\n\n\n\t\t\t歡迎進入在線考試系統!\n\n\n\n\n\n");
printf("\t\t\t按任意鍵進入主頁面----->");
getch();
system("cls");
menu(); //進入選單顯示出選擇系統的界面
scanf("%d",&a);
while(a)
{
switch(a) //選擇系統
{
case 1:printf("老師開始增加題目\n");ent_a();system("cls");teacher(text);system("cls");break;
case 2:printf("學生開始考試\n");ent_s();system("cls");student(text);system("cls");break;
case 3:printf("題庫中的題目\n");ent_a();print();printf("\n\n按任意鍵回傳選單\n");getch();system("cls");break;
default:printf("輸入錯誤!");system("cls");menu;break;
}
menu();
scanf("%d",&a);
}
system("cls");printf("\n\n\n\n\n\n\n\n\n\t\t\t歡迎下次使用魯川系統!\n\n\n\n\n\n\n\n\n\n");
}
void menu() //友好界面選單欄
{
printf("\t\t\t******************************\n");
printf("\t\t\t* 單項選擇題標準化考試系統 *\n");
printf("\t\t\t* *\n");
printf("\t\t\t******* 功能選單 *********\n");
printf("\t\t\t** **\n");
printf("\t\t\t** **\n");
printf("\t\t\t** 輸入編號選擇使用相應功能 **\n");
printf("\t\t\t** **\n");
printf("\t\t\t** **\n");
printf("\t\t\t******************************\n");
printf("\t\t\t* 1.【老師增加題目】 *\n");
printf("\t\t\t* 2.【學生抽題開始考試】 *\n");
printf("\t\t\t* 3.【查詢題庫中的所有題目】*\n");
printf("\t\t\t* 0.【退出系統】 *\n");
printf("\t\t\t******************************\n");
printf("請選擇功能:");
}
void ent_a()
{
char key[10],password[10]="12345678";
int k=1;
while(k<=3)
{ system("cls");
printf("\n\n\t\t\t\t請教師輸入您的密碼:\n");
scanf("%s",key);
if(strcmp(password,key)==0)
{
return 0;
}
else
{
k++;
if(k>3)
{printf("\t\t\t\t輸入密碼錯誤三次,系統將自動退出!\n");
exit(0);}
else
{printf("\t\t\t\t密碼錯誤!請再次輸入:\n");continue;}
}
}
}
void ent_s()
{
char key[10],password[10]="12345678";
int k=1;
while(k<=3)
{ system("cls");
printf("\n\n\t\t\t\t請學生輸入你的密碼:\n");
scanf("%s",key);
if(strcmp(password,key)==0)
{
return 0;
}
else
{
k++;
if(k>3)
{printf("\t\t\t\t輸入密碼錯誤三次,系統將自動退出!\n");
exit(0);}
else
{printf("\t\t\t\t密碼錯誤!請再次輸入:\n");continue;}
}
}
}
void teacher(TEXT text[]) /*教師系統*/
{
int i;
fp=fopen("C:\danxuanti.txt","a+");
printf("\n\n\n\n\t\t\t請老師在此題庫中輸入題目:\n");
for(i=0;i<1000;i++)
{
printf("輸入題目(end結束):\n"); /*輸入題目資訊*/
scanf("%s",text[i].topic);
if(strcmp(text[i].topic,"end")==0) /*判斷是否結束檔案*/
{
fclose(fp);
return 0;
}
printf("輸入答案A:\n"); /*輸入題目答案以及正確答案*/
scanf("%s",text[i].a);
printf("輸入答案B:\n");
scanf("%s",text[i].b);
printf("輸入答案C:\n");
scanf("%s",text[i].c);
printf("輸入答案D:\n");
scanf("%s",text[i].d);
printf("輸入正確答案(請輸入A、B、C、D):\n");
scanf("%s",text[i].rightanswer);
N++;
fprintf(fp,"%d.%s\n\nA.%s\nB.%s\nC.%s\nD.%s\nrightanswer:%s\n\n",N,text[i].topic,text[i].a,text[i].b,text[i].c,text[i].d,text[i].rightanswer);
} /*將題目的資訊存放在檔案中*/
fclose(fp);
}
void student(TEXT text[]) //學生系統
{
int n;
if(fp=fopen("C:\danxuanti.txt","r")==NULL)
{
N=0;
printf("該題庫無題目請先添加題目,按任意鍵回傳!");
getch();
system("cls");
return 0;
}
printf("請輸入答題數目(格式為正整數):[ ]\b\b");
scanf("%d",&n);
readfromfile(n);
}
void readfromfile(int n)
{ char answer[2];
int count,i;
double c;
FILE *fp;
TEXT text;
int number;
srand((unsigned) time(NULL)); //用時間做種,每次產生亂數不一樣
number = rand() % (N+1); //產生0-100的亂數
if((fp=fopen("danxuanti.txt","r"))==NULL)
{
printf("failure to open the txt!");
exit(0);
}
for(i=0;i<n;i++,number++)
{ fseek(fp,(number-1)*sizeof(struct text1),SEEK_SET);
fread(&text,sizeof(struct text1),1,fp);
printf("%d.%s\n\nA.%s\nB.%s\nC.%s\nD.%s\nrightanswer:%s\n\n",i+1,text.topic,text.a,text.b,text.c,text.d,text.rightanswer);
printf("請輸入你的答案:\n");
scanf("%s",answer);
if(strcmp(text.rightanswer,answer)==0)
{
printf("恭喜你回答正確!");
count++;
}
else printf("回答錯誤!正確答案是:%s",text.rightanswer);
}
c=count/n;
printf("你的正確率為%f",c);
fclose(fp);
getch();
}
void print()
{
FILE *fp = fopen("C:\danxuanti.txt", "r");
int c;
while((c=fgetc(fp))!=EOF) putchar(c);
printf("以上為題庫中的題目\n");
}
uj5u.com熱心網友回復:
基本的要求是這些單項選擇題測驗系統 1、 用檔案保存試題庫,每個試題包括題干、4 個備選答案、標準答案; 2、 試題輸入,增加試題到試題庫中; 3、 試題抽取,每次從試題庫中抽出 n 道題(n 由鍵盤輸入) ; 4、 答題,用戶輸入自己的答案; 5、 自動判卷,系統可根據用戶答案與標準答案的對比實作判卷并給出成績。
uj5u.com熱心網友回復:
有點亂 你可以排好點嗎
uj5u.com熱心網友回復:
void ent_a()
{
char key[10], password[10]="12345678";
int k=1;
while(k<=3)
{ system("cls");
printf("\n\n\t\t\t\t請教師輸入您的密碼:\n");
scanf("%s",key);
if(strcmp(password,key)==0)
{
//return 0;
return;
}
else
{
k++;
if(k>3)
{
printf("\t\t\t\t輸入密碼錯誤三次,系統將自動退出!\n");
exit(0);
}
else
{
printf("\t\t\t\t密碼錯誤!請再次輸入:\n");
continue;
}
}
}
}
函式定義為void回傳值,因此不能return 0;把0去掉即可;
同理ent_s也是同樣的問題;
void teacher(TEXT text[]) /*教師系統*/
{
int i;
fp=fopen("C:\danxuanti.txt","a+");
if (!fp)
exit(0);
printf("\n\n\n\n\t\t\t請老師在此題庫中輸入題目:\n");
//for(i=0;i<1000;i++)
for(i=0;i<100;i++)
{
printf("輸入題目(end結束):\n"); /*輸入題目資訊*/
scanf("%s",text[i].topic);
if(strcmp(text[i].topic,"end")==0) /*判斷是否結束檔案*/
{
fclose(fp);
//return 0;
return;
}
printf("輸入答案A:\n"); /*輸入題目答案以及正確答案*/
scanf("%s",text[i].a);
printf("輸入答案B:\n");
scanf("%s",text[i].b);
printf("輸入答案C:\n");
scanf("%s",text[i].c);
printf("輸入答案D:\n");
scanf("%s",text[i].d);
printf("輸入正確答案(請輸入A、B、C、D):\n");
scanf("%s",text[i].rightanswer);
N++;
fprintf(fp,"%d.%s\n\nA.%s\nB.%s\nC.%s\nD.%s\nrightanswer:%s\n\n",N,text[i].topic,text[i].a,text[i].b,text[i].c,text[i].d,text[i].rightanswer);
} /*將題目的資訊存放在檔案中*/
fclose(fp);
}
參考一下這個,一個問題是函式是void回傳值,因此return 0;是和定義矛盾的。解決方法也是去掉0;
檔案打開之后需要判斷fp,保證檔案是打開成功的。main函式里定義的text是100長度,因此這兒的回圈不能超過100,否則會導致陣列越界;
void student(TEXT text[]) //學生系統
{
int n;
//if(fp=fopen("C:\danxuanti.txt","r")==NULL)
if((fp=fopen("C:\danxuanti.txt","r"))==NULL)
{
N=0;
printf("該題庫無題目請先添加題目,按任意鍵回傳!");
getch();
system("cls");
//return 0;
return;
}
printf("請輸入答題數目(格式為正整數):[ ]\b\b");
scanf("%d",&n);
readfromfile(n);
}
如上改動;同樣的問題,定義的是void,卻回傳0;另一個問題,注意if里運算式的優先級,若這樣寫:
if(fp=fopen("C:\danxuanti.txt","r")==NULL)優先級是fopen的回傳值與NULL比較,然后將比較之后的結果賦值給fp;
另外一個問題,該函式內打開了檔案卻沒有關閉;
void readfromfile(TEXT text[], int n)
{
if (n > 100)
return;
char answer[2];
//int count,i;
int count = 0, i, idx;
double c;
FILE *fp;
//TEXT text;
int number;
srand((unsigned) time(NULL)); //用時間做種,每次產生亂數不一樣
number = rand() % (N+1); //產生0-100的亂數
if((fp=fopen("danxuanti.txt","r"))==NULL)
{
printf("failure to open the txt!");
exit(0);
}
//for(i=0;i < n;i++,number++)
for(i=0;i < n && number < 100;i++,number++)
{
//fseek(fp,(number-1)*sizeof(struct text1),SEEK_SET);
//fread(&text,sizeof(struct text1),1,fp);
idx = number-1;
//printf("%d.%s\n\nA.%s\nB.%s\nC.%s\nD.%s\nrightanswer:%s\n\n",i+1,text.topic,text.a,text.b,text.c,text.d,text.rightanswer);
printf("%d.%s\n\nA.%s\nB.%s\nC.%s\nD.%s\nrightanswer:%s\n\n",i+1,text[idx].topic,text[idx].a,text[idx].b,text[idx].c,text[idx].d,text[idx].rightanswer);
printf("請輸入你的答案:\n");
scanf("%s",answer);
if(strcmp(text[idx].rightanswer,answer)==0)
{
printf("恭喜你回答正確!");
count++;
}
else
printf("回答錯誤!正確答案是:%s",text[idx].rightanswer);
}
//c=count/n;
c=count * 1.0 / n;
printf("你的正確率為%f",c);
fclose(fp);
getch();
}
對比參考一下吧
cout未初始化,count/n計算的是整型,要轉成double型別,需要count * 1.0 / n;
上面寫入檔案是用fprintf,但是讀的時候卻用fread,格式不對稱,自然讀到的資料也不一定完全和寫入的一樣。
與其去讀檔案,不如直接使用上面輸入的text;
注意輸入的n不要超過100,否則會導致陣列越界。
基礎還需要加強學習,代碼比較亂。首先自己要解決編譯出現的錯誤;
uj5u.com熱心網友回復:
謝謝謝謝啦,剛剛按照您的方法又改了改,其他地方都懂了,可是用vc++編譯出來還是學生系統的readfromfile函式編輯出現錯誤了。我的想法是將檔案按照結構體的方式輸入檔案中,然后再將檔案中的指標隨機指向一個結構體然后輸出想要抽的幾道題出來。
第一次寫這么長的程式所以寫的有點亂亂的,網上也借鑒了很多的方法可就是沒有寫出來的。
uj5u.com熱心網友回復:
第一次發帖不是很懂

在我的vc上面看著還是好的格式發出來就是錯的了
這是改了一點點后的程式呢
#include<stdio.h>
#include<stdlib.h>
#include <time.h>
int N; //題目的數量
typedef struct text1 //將題目定義為結構體
{int num; //題號
char topic[50]; //題目
char a[10],b[10],c[10],d[10]; //ABCD四個選項
char rightanswer[2]; //正確答案
}TEXT;
void teacher(TEXT text[]); //教師系統
void writetofile(TEXT text[],int i); //資料塊寫檔案
void student(TEXT text[]); //學生系統
void readfromfile(int n); //資料塊讀檔案
void menu(); //主選單
void print();
void ent_a();
void ent_s();
FILE *fp;
void main()
{ TEXT text[100];
int a;
printf("\n\n\n\n\n\n\n\t\t\t歡迎進入在線考試系統!\n\n\n\n\n\n");
printf("\t\t\t按任意鍵進入主頁面----->");
getch();
system("cls");
menu(); //進入選單顯示出選擇系統的界面
scanf("%d",&a);
while(a)
{
switch(a) //選擇系統
{
case 1:printf("老師開始增加題目\n");ent_a();system("cls");teacher(text);system("cls");break;
case 2:printf("學生開始考試\n");ent_s();system("cls");student(text);system("cls");break;
case 3:printf("題庫中的題目\n");ent_a();print();printf("\n\n按任意鍵回傳選單\n");getch();system("cls");break;
default:printf("輸入錯誤!");system("cls");menu;break;
}
menu();
scanf("%d",&a);
}
system("cls");printf("\n\n\n\n\n\n\n\n\n\t\t\t歡迎下次使用魯川系統!\n\n\n\n\n\n\n\n\n\n");
}
void menu() //友好界面選單欄
{
printf("\t\t\t┏━━━━━━━━━━━━━━┓\n");
printf("\t\t\t┃ 單項選擇題標準化考試系統 ┃\n");
printf("\t\t\t┃ ┃\n");
printf("\t\t\t┃┏━━━ 功能選單 ━━━┓┃\n");
printf("\t\t\t┃┃ ┃┃\n");
printf("\t\t\t┃┃ ┃┃\n");
printf("\t\t\t┃┃輸入編號選擇使用相應功能┃┃\n");
printf("\t\t\t┃┃ ┃┃\n");
printf("\t\t\t┃┃ ┃┃\n");
printf("\t\t\t┃┗━━━━━━━━━━━━┛┃\n");
printf("\t\t\t┃ 1.【老師增加題目】 ┃\n");
printf("\t\t\t┃ 2.【學生抽題開始考試】 ┃\n");
printf("\t\t\t┃ 3.【查詢題庫中的所有題目】┃\n");
printf("\t\t\t┃ 0.【退出系統】 ┃\n");
printf("\t\t\t┗━━━━━━━━━━━━━━┛\n");
printf("請選擇功能:");
}
void ent_a()
{
char key[10],password[10]="12345678";
int k=1;
while(k<=3)
{ system("cls");
printf("\n\n\t\t\t\t請教師輸入您的密碼:\n");
scanf("%s",key);
if(strcmp(password,key)==0)
{
return;
}
else
{
k++;
if(k>3)
{printf("\t\t\t\t輸入密碼錯誤三次,系統將自動退出!\n");
exit(0);}
else
{printf("\t\t\t\t密碼錯誤!請再次輸入:\n");continue;}
}
}
}
void ent_s()
{
char key[10],password[10]="12345678";
int k=1;
while(k<=3)
{ system("cls");
printf("\n\n\t\t\t\t請學生輸入你的密碼:\n");
scanf("%s",key);
if(strcmp(password,key)==0)
{
return;
}
else
{
k++;
if(k>3)
{printf("\t\t\t\t輸入密碼錯誤三次,系統將自動退出!\n");
exit(0);}
else
{printf("\t\t\t\t密碼錯誤!請再次輸入:\n");continue;}
}
}
}
void teacher(TEXT text[]) /*教師系統*/
{
int i;
fp=fopen("C:\danxuanti.txt","a+");
printf("\n\n\n\n\t\t\t請老師在此題庫中輸入題目:\n");
for(i=0;i<100;i++)
{
printf("輸入題目(end結束):\n"); /*輸入題目資訊*/
scanf("%s",text[i].topic);
if(strcmp(text[i].topic,"end")==0) /*判斷是否結束檔案*/
{
fclose(fp);
return;
}
printf("輸入答案A:\n"); /*輸入題目答案以及正確答案*/
scanf("%s",text[i].a);
printf("輸入答案B:\n");
scanf("%s",text[i].b);
printf("輸入答案C:\n");
scanf("%s",text[i].c);
printf("輸入答案D:\n");
scanf("%s",text[i].d);
printf("輸入正確答案(請輸入A、B、C、D):\n");
scanf("%s",text[i].rightanswer);
N++;
fprintf(fp,"%d.%s\n\nA.%s\nB.%s\nC.%s\nD.%s\nrightanswer:%s\n\n",N,text[i].topic,text[i].a,text[i].b,text[i].c,text[i].d,text[i].rightanswer);
} /*將題目的資訊存放在檔案中*/
fclose(fp);
}
void student(TEXT text[]) //學生系統
{
int n;
if((fp=fopen("C:\danxuanti.txt","r"))==NULL)
{
N=0;
printf("該題庫無題目請先添加題目,按任意鍵回傳!");
getch();
system("cls");
return;
}
printf("請輸入答題數目(格式為正整數):[ ]\b\b");
scanf("%d",&n);
readfromfile(n);
fclose(fp);
}
void readfromfile(int n)
{
char answer[2];
int count=0,i,idx;
double c;
FILE *fp;
int number;
if(n>100)
return;
srand((unsigned) time(NULL)); //用時間做種,每次產生亂數不一樣
number = rand() % (N+1); //產生0-100的亂數
if((fp=fopen("danxuanti.txt","r"))==NULL)
{
printf("failure to open the txt!");
exit(0);
}
for(i=0;i<n&&number<100;i++,number++)
{
fscanf(fp,"%d.%s\n\nA.%s\nB.%s\nC.%s\nD.%s\nrightanswer:%s\n\n",i+1,text[idx].topic,text[idx].a,text[idx].b,text[idx].c,text[idx].d,text[idx].rightanswer);
printf("%d.%s\n\nA.%s\nB.%s\nC.%s\nD.%s\nrightanswer:%s\n\n",i+1,text[idx].topic,text[idx].a,text[idx].b,text[idx].c,text[idx].d,text[idx].rightanswer);
printf("請輸入你的答案:\n");
scanf("%s",answer);
if(strcmp(text[idx].rightanswer,answer)==0)
{
printf("恭喜你回答正確!");
count++;
}
else printf("回答錯誤!正確答案是:%s",text[idx].rightanswer);
}
c=count*1.0/n;
printf("你的正確率為%f",c);
fclose(fp);
getch();
}
void print()
{
FILE *fp = fopen("C:\danxuanti.txt", "r");
int c;
while((c=fgetc(fp))!=EOF) putchar(c);
printf("以上為題庫中的題目\n");
}
uj5u.com熱心網友回復:
printf里面的%和變數的一一對應關系scanf里面的%和變數以及變數前加不加&的一一對應關系
是C代碼中非常容易出錯的地方,而且通常編譯還不出錯。
所以在編譯源代碼之前值得專門仔細檢查一遍甚至多遍。
在每個最后不帶\n的printf后面加fflush(stdout);
在每個不想受接識訓沖區舊內容影響的scanf前面加rewind(stdin);
另外請檢查scanf的回傳值。
//請今后要用
char c;
scanf("%c",&c);
//時,都改為
char s[2];
char c;
scanf("%1s",s);
c=s[0];
//自動跳過一個或多個空格或Tab字符或回車換行,讀取下一個字符。
uj5u.com熱心網友回復:
可以看一下這篇文章《C語言大作業之超市管理系統》 https://www.weupgo.cn/?p=545,有原始碼。轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/78778.html
標籤:C語言
