2018级A卷
1.输出S的值,精度1e-6
#include <stdio.h>
int main()
{
int i = 1;
double taylor = 1 / (1.0 * (2 * i - 1)) * (1.0 * (2 * i) ) / (2 * i - 1); //求出每一项的值
double sum = 0;
while(taylor > 1e-6)
{
sum += taylor;
i = i + 1;
taylor = 1 / (1.0 * (2 * i - 1)) * (1.0 * (2 * i) ) / (2 * i - 1); //更新taylor
}
printf("%lf",sum);
return 0;
}
2.编写函数,对n个字符串按字典顺序排序
限定函数名void sort(char st[ ][10], int n)
算法思想:
对二维字符串进行冒泡排序,比较两个字符串,将ASCII码较小的元素放在前面即可
字符串的复制选择的是strcpy写法,比较选择的是strcmp写法
int strcmp(char* str1, char* str2)
{
int i = 0;
do{
if(str1[i] > str2[i])
return 1;
else if(str1[i] < str2[i])
return -1;
i++;
}while(str1[i] != '\0' && str2[i] != '\0');
if(str1[i] == '\0' && str2[i] == '\0')
return 0;
else
if(str1[i] == '\0')
return 1;
return -1;
}
void strcpy(char* s1, char *s2)
{
int i = 0;
while(s1[i] != '\0')
{
s2[i] = s1[i];
i++;
}
s2[i] = '\0'; //为S2加上结束符
}
void sort(char st[][10], int n)
{
char temp[10];
for(int i = n-1; i > 0; i--) //对n个字符串采用冒泡排序
for(int j = 0; j < i; j++)
{
if(strcmp(st[j],st[j+1]) == 1)
{
strcpy(st[j],temp); //将st[j]复制给temp临时保存
strcpy(st[j+1],st[j]); //将st[j+1]的值复制给st[j]
strcpy(temp,st[j+1]); //将temp的值复制给st[j+1]
}
}
}
3.编写递归函数,实现对有序数组的二分查找
int search(int a[], int left, int right, int key)
{
if(left <= right)
{
int mid = (left + right) / 2;
if(nums[mid] == key)
return mid;
if(nums[mid] < key)
return binarysearch(a,mid+1, right, key); //向右查找
return binarysearch(a,left,mid-1, key); //向左查找
}
return -1;
}
int binarysearch(int a[], int n, int key){
if(numsSize == 0)
return -1;
return binarysearch(a,0,n-1,key);
}
4.成绩信息包含:姓名,学号,讨论成绩,报告成绩,测试成绩五项信息,规定:
实验成绩 = 讨论成绩(20%)+报告成绩(20%)+测试成绩 (60%)
1)创建结点类型;
2)假如所有信息都存储在文件2018.txt中,创建链表;
3)对题中的里链表按实验成绩,从高到低排序
1.头文件两分,为采分点
#include <stdlib.h>
#include <stdio.h>
#define N 20
struct Node{
int num; //学号
char name[N]; //姓名
int discuss; //讨论成绩
int report; //报告成绩
int test; //测试成绩
float exp; //实验成绩
struct Node *next;
}
struct Node* Create(); //从文件创建链表函数
{
FILE *fp;
if((fp=fopen("2018.txt","r"))==NULL)
{
printf("\n文件打开失败");
exit(0);
}
struct Node *head = (struct Node*)malloc(sizeof(struct Node)); //创建头结点
head -> next = NULL;
struct Node *p;
while(!feof(fp))
{
p = (struct Node*)malloc(sizeof(struct Node));
fscanf(fp,"%s %d %d %d %d %f",p->name,&p->num,&p->discuss,&p->report,&p->test,&p->exp);
p -> next = head -> next;
head -> next = p;
}
fclose(fp); //关闭文件
return head -> next;
}
struct Node* Sort(struct Node* head){
if(head == NULL ||head -> next == NULL)
return head;
struct Node* dummyhead = (struct Node*)malloc(sizeof(struct Node));
dummyhead -> next = head;
struct Node* p = head -> next, *pre = dummyhead;
head -> next = NULL;
while(p != NULL)
{
struct Node* temp = p -> next; //保存p的后继
while(pre -> next != NULL && pre -> next -> exp > p -> exp) //比较实验成绩,将其插入至合适的位置
pre = pre -> next;
p -> next = pre -> next;
pre -> next = p;
p = temp; //还原p
pre = dummyhead; //将pre重置为最高实验成绩的位置
}
return dummyhead -> next;
}
2010级B卷
1.编一函数,求一个NXM的二维整形数组中各元素的平均值和最大值。
#include <stdio.h>
void AverageAndMax(int a[N][M])
{
int sum = 0, max = a[0][0];
for(int i = 0; i < N; i++)
for(int j = 0; j < M; j++)
{
sum += a[i][j];
if(a[i][j] > max)
max = a[i][j];
}
printf("平均值为%f,最大值为%d\n",(1.0 * sum) / (M * N),max);
}
2.编一函数,完成NXN的整形数组 a的赋值,其中,a的各元素值如下图所示,未显示的其他元素值均为0.
1
2 4
3 6 9
4 8 12 16
5 10 15 20 25
6 12 18 24 30 36
7 14 21 28 35 45 49
8 16 24 32 40 48 56 64
9 18 27 36 45 54 63 72 81
#include <stdio.h>
#include <malloc.h>
int** caculate(int N)
{
int** a = (int**)malloc(sizeof(int*) * 9);
for(int i = 0; i < 9; i++)
a[i] = (int*)malloc(sizeof(int) * 9);
for(int i = 0; i < 9; i++)
for(int j = 0; j < 9; j++)
{
if(i >= j)
a[i][j] = (i+1) * (j+1);
else
a[i][j] = 0;
}
return a;
}
int main()
{
int** a = caculate(9);
for(int i = 0; i < 9; i++)
{
for(int j = 0; j < 9; j++)
{
if(i >= j && a[i][j] <= 9)
printf("%d ",a[i][j]);
else if(i >= j)
printf("%d ",a[i][j]);
}
printf("\n");
}
return 0;
}
3.编写一个递归函数,计算f(n)=r1!+r2!+r3!+r4!,其中r1,r2,r3,r4都是n的各个数位。
#include <stdio.h>
int fac(int n)
{
if(n == 1)
return 1;
return n*fac(n-1);
}
int f(int n)
{
if(n == 0)
return 0;
int temp = n % 10;
return fac(temp) + f(n / 10);
}
4.编一函数,完成对字符串参数的判断,如果该字符是对称字符串,函数值返回1,如果不是则返回零。
算法思想:
1.设置双指针i,j分别指向字符串头和字符串尾
2.当表头与表尾指针i,j未相遇时,判断遍历到元素是否相等,若相等则指针继续相向前进,否则返回0
3.若执行结束则返回1
int isPalindrome(char * s){
int len = strlen(s);
int i = 0, j = len - 1;
while(i < j)
{
if(i < j && s[i] != s[j])
return 0;
i++;
j--;
}
return 1;
}
5.某班学生的信息包括学号、姓名、性别、成绩等信息。
1)完成学生信息的结构定义;
2)编写一个名为CreatList的函数实现建立具有n个节点的链表来存储这个班的学生信息;
3)编一函数WriteFile,将该班的信息存入文件。
struct Node{
int num; //学号
char name[10]; //姓名
int sex; //性别
int score; //成绩
struct Node* next;
}
struct Node* CreatList(int n)
{
struct Node* head = (struct Node*)malloc(sizeof(struct Node));
//虚拟头结点,用于头插法
head -> next = NULL;
for(int i = 0; i < n; i++)
{
struct Node* p = (struct Node*)malloc(sizeof(struct Node));
scanf("%d %s %d %d",&(p -> num),p -> name, &(p -> sex), &(p -> score));
p -> next = head -> next;
head -> next = p;
}
return head -> next;
}
void WriteFile(struct Node* head)
{
FILE* fp;
if((fp = fopen("write.txt","w")) == NULL)
{
printf("文件打开错误\n");
exit(0);
}
struct Node* p = head;
while(p != NULL)
{
fprintf(fp,"姓名:%s",p -> name);
fprintf(fp,"学号:%d",p -> num);
fprintf(fp,"性别:");
if(p -> sex == 1)
fprintf(fp,"男");
else
fprintf(fp,"女");
fprintf(fp,"成绩: %d\n",&(p->score));
p = p -> next;
}
fclose(fp);
}
2004级A卷
1.编程序,打印前十对孪生素数。若两个素数之差为2,则称为孪生素数,例如(3,5)(5,7)(11,13)
#include <stdio.h>
#include <math.h>
bool isprime(int n) //判断是否为素数
{
if(n <= 1)
return false;
if(n == 2)
return true;
for(int i = 2; i <= sqrt(n); i++)
if(n % i == 0)
return false;
return true;
}
void temprime(int n)//打印前10对孪生素数
{
int pre = 2, p, count = 0; //pre表示前一个素数,p表示当前素数,count表示孪生素数的对数
for(int i = 3; count < n; i += 2)
if(isprime(i))
{
if(i - pre == 2)
{
printf("%d 和 %d 是孪生素数\n", pre, i);
count++;
}
pre = i; //对前一个素数进行更新
}
}
int main()
{
temprime(10);
return 0;
}
2.设幂数为非负整数的多项式。将每一项的系数和幂次存于下表:
#include <stdio.h>
struct PX{
int pow; //幂
float coe; //系数
};
float CountPX(struct PX p[], int x)
{
float result = 0, temp;
int i = 0;
while(p[i].pow > 0)
{
temp = p[i].coe; //先保存为系数
for(int j = 0; j < p[i].pow; j++)
temp *= x; //乘以x的次方
result += temp;
i++;
}
if(p[i].pow == 0)
result += p[i].coe;
return result;
}
测试用例
int main()
{
struct PX p[20];
p[0].pow = 5;
p[0].coe = 3.0;
p[1].pow = 3;
p[1].coe = 4.2;
p[2].pow = 2;
p[2].coe = 2.1;
p[3].pow = 0;
p[3].coe = 7;
printf("%0.2f",CountPX(p,2));
}
3.编程序判断10阶整数方阵是否关于主对角线对称
#include <stdio.h>
bool issymmetry(int matrix[][10])
{
for(int i = 0; i < 10; i++)
{
for(int j = 0; j < i; j++)
if(matrix[i][j] != matrix[j][i])
return false;
}
return true;
}
int main()
{
int matrix[10][10];
for(int i = 0; i < 10; i++)
{
for(int j = 0; j < 10; j++)
scanf("%d",&matrix[i][j]);
}
if(issymmetry(matrix))
printf("矩阵是对称的");
else
printf("矩阵不对称");
}
4.编写一个函数,用递归计算Hermite多项式的函数,Hermite多项式定义为
double Herrnite(int n, int x)
{
if(n == 0) return 1;
if(n == 1) return 2 * x;
return 2 * x * Herrnite(n-1,x) + 2 * (n - 1) * Herrnite(n-2,x);
}
5.编函数,用冒泡实现由整数组成的单向链表的排序
算法思想:冒牌排序
1.建立一个虚拟头结点dummyhead,设置p指向第一个结点,pre为p的前驱结点,遍历一遍链表求出长度
2.遍历整个链表,当p指向的元素与其后继元素反序时,交换二者,同时更新标记为已经交换过
3.结束时返回第一个结点
int listlen(struct ListNode* head)
{
int count = 0;
while(head != NULL)
{
count++;
head = head -> next;
}
return count;
}
struct ListNode* insertionSortList(struct ListNode* head){
if(head == NULL || head -> next == NULL)
return head;
int len = listlen(head);
struct ListNode* dummyhead = (struct ListNode*)malloc(sizeof(struct ListNode));
dummyhead -> next = head;
for(int i = len - 1; i > 0; i--)
{
struct ListNode* p = dummyhead -> next, *pre = dummyhead;
bool swap = false;
for(int j = 0; j < i; j++)
{
if(p -> val > p -> next -> val)
{
struct ListNode* q = p -> next;
pre -> next = q;
pre = q;
p -> next = q -> next;
q -> next = p;
swap = true;
}
else
{
pre = p;
p = p -> next;
}
}
if(swap == false)
break;
}
return dummyhead -> next;
}
2005级
1.编写函数,判断两个整数是否互质,其中求两个正整数M、N的最大公约数使用辗转相除法
int gcd(int a, int b)
{
while(b != 0)
{
int temp = a % b;
a = b;
b= temp;
}
return a;
}
int gcd2(int a, int b)
{
if(b == 0)
return a;
return gcd2(b, a % b);
}
bool isprime(int a, int b)
{
if(gcd(a,b) == 1)
return true;
return false;
}
2.编程序,打印所有三位的Armstrong数,所谓Armstrong数是指其值等于它本身每位数字立方和的数。如:
#include <stdio.h>
int main()
{
for(int i = 100; i < 1000; i++)
{
int m = i, sum = 0;
while(m != 0)
{
sum += (m % 10) * (m % 10) * (m % 10);
m /= 10;
}
if(sum == i)
printf("%d ",i);
}
}
3.编写一个递归函数,实现在已递增排序的整数数组中进行二分检索
答案参见2018级第三题
4.一个整数可以表示成图一的形式(符号有两种可能:+,-)
①设计这种表示法的数据类型。②并编写函数判断任意给定两个整数的大小
#include <stdio.h>
#include <malloc.h>
struct LNode{
int val;
struct LNode* next;
};
struct Linklist{
int sign; //符号
int len; //位次
struct LNode* pd;
};
int compare(struct Linklist* a, struct Linklist* b)
{
if(a -> sign == 1 && b -> sign == -1) return 1;
if(a -> sign == -1 && b -> sign == 1) return -1;
if(a -> sign == -1 && b -> sign == -1)
{
if(a -> len > b -> len) return -1;
if(a -> len < b -> len) return 1;
}
if(a -> sign == 1 && b -> sign == 1)
{
if(a -> len < b -> len) return -1;
if(a -> len > b -> len) return 1;
}
struct LNode *p = a -> pd, *q = b -> pd;
while(p != NULL && q != NULL)
{
if(p -> val > q -> val)
{
if(a -> sign == -1 && b -> sign == -1) return -1;
if(a -> sign == 1 && b -> sign == 1) return 1;
}
else if(p -> val < q -> val)
{
if(a -> sign == -1 && b -> sign == -1) return 1;
if(a -> sign == 1 && b -> sign == 1) return -1;
}
p = p -> next;
q = q -> next;
}
return 0;
}
调用程序
int main()
{
struct Linklist *a = (struct Linklist*)malloc(sizeof(struct Linklist));
struct Linklist *b = (struct Linklist*)malloc(sizeof(struct Linklist));
printf("\n请输入链表a的符号,长度\n");
scanf("%d",&(a -> sign));
scanf("%d",&(a -> len));
struct LNode* head = (struct LNode*)malloc(sizeof(struct LNode));
head -> next = NULL;
for(int i = 0; i < 5; i++)
{
struct LNode* p = (struct LNode*)malloc(sizeof(struct LNode));
p -> next = head -> next;
head -> next = p;
}
a -> pd = head -> next;
head = head -> next;
for(int i = 0; i < 5; i++)
{
scanf("%d",&head -> val);
head = head -> next;
}
printf("\n请输入链表b的符号,长度\n");
scanf("%d %d",&(b -> sign),&(b -> len));
struct LNode* head2 = (struct LNode*)malloc(sizeof(struct LNode));
head2 -> next = NULL;
for(int i = 0; i < 5; i++)
{
struct LNode* p = (struct LNode*)malloc(sizeof(struct LNode));
p -> next = head2 -> next;
head2 -> next = p;
}
b -> pd = head2 -> next;
head2 = head2 -> next;
for(int i = 0; i < 5; i++)
{
scanf("%d",&head2 -> val);
head2 = head2 -> next;
}
if(compare(a,b) == 1)
printf("a链表更大");
else if(compare(a,b) == -1)
printf("b链表更大");
else
printf("一样的");
// struct LNode* show = b -> pd;
// printf("\nb链表的符号为%d,长度为%d\n",a->sign,a->len);
// while(show != NULL)
// {
// printf("%d ",show -> val);
// show = show -> next;
// }
}
2006级
1.编写函数,数列
的前n项和。例如当n等于5时s(5) = 1 - 1/2 + 1/3 - 1/4 + 1/5
float S(int n)
{
float sum = 0;
int sign = 1;
for(int i = 1; i <= n; i++)
{
sum += 1.0* sign / i;
sign *= -1;
}
return sum;
}
2.编程序判断10阶整数方阵是否关于主对角线对称
答案参见2004级第三题
3.编写函数比较两个字符串的大小,当s1>s2时,返回1,s1<s2时,返回-1,否则s1=s2时,返回0
int strcmp(char* s1, char* s2)
{
int i = 0;
while(s1[i] != '\0' && s2[i] != '\0')
{
if(s1[i] > s2[i])
return 1;
else if(s1[i] < s2[i])
return -1;
i++;
}
if(s1[i] == '\0' && s2[i] == '\0')
return 0;
else if(s1[i] == '\0')
return 1;
return -1;
}
4.编写函数计算如下多项式的第n项值
答案参见2004级第四题
5.把一个由数字和字母构成的字符串用单链表存储,每一个结点存储一个字符,请完成如下功能:
①:请给出节点的数据结构的定义
②:编写一个奖链表中所有数字串到前面,而字母串到后面,且数字与数字,字母与字母相对顺序不变。
struct LinkNode{
char ch; //保存字符
struct LinkNode* next;
};
struct LinkNode* revise(struct LinkNode* head)
{
struct LinkNode* arghead = (struct LinkNode*)malloc(sizeof(struct LinkNode));
arghead -> next = NULL;
struct LinkNode* dighead = (struct LinkNode*)malloc(sizeof(struct LinkNode));
dighead -> next = NULL;
struct LinkNode *rear1 = arghead, *rear2 = dighead;
struct LinkNode* p = head;
while(p != NULL)
{
struct LinkNode* temp = p -> next;
if(p -> ch >= 'a' && p -> ch <= 'z' || p -> ch >= 'A' && p -> ch <= 'Z')
{
p -> next = rear1 -> next;
rear1 -> next = p;
rear1 = p;
}
else
{
p -> next = rear2 -> next;
rear2 -> next = p;
rear2 = p;
}
p = temp;
}
//链接两个链表,rear2的后继指向arghead的后继
rear2 -> next = arghead -> next;
return dighead -> next;
}
2007级
1.验证角谷猜想:任意给定一个整数,若为偶数则除以2;若为奇数则乘三再加一,得到一个新的自然数之后按照上面的法则继续演算,若干次后得到的结果必为1。
#include <stdio.h>
int main()
{
int n, count = 0;
scanf("%d",&n);
do{
if(n % 2 == 1)
{
printf("%d * 3 + 1 = %d\n",n,n*3+1);
n = n * 3 + 1;
}
else
{
printf("%d / 2 = %d\n",n,n/2);
n /= 2;
}
count++;
}while(n != 1);
printf("经过了%d次角谷变换",count);
}
2.编程实现:输入正整数N,若N在1~20之间,则输出相应数字的英文单词,否则输出提示信息overflow。如:输入1,输出one,输入25,输出overflow。
要求:使用字符串数组,保存相应输出的英文字符串;且必须使用此数组实现上述功能
#include <stdio.h>
char a[21][10] = {{"overflow"},{"one"},{"two"},{"three"},{"four"},{"five"},{"six"},{"seven"},{"eight"},{"nine"},{"ten"},{"eleven"},
{"twelve"},{"thirteen"},{"fourteen"},{"fifteen"},{"sixteen"},{"seventeem"},{"eighteen"},{"nineteem"},{"twenty"}};//建立对照英文表
int main()
{
int N;
scanf("%d",&N);
printf("%d = ",N);
if(N >= 1 && N <= 20)
printf("%s",a[N]);
else
printf("%s",a[0]);
}
3.从键盘上输入一个字符串,把该字符串中的小写字母转换成大写字符,并将变换后的字符串输出的文件test.txt中,编程实现上述功能
#include <stdlib.h>
#include <stdio.h>
int main()
{
FILE* fp;
char str[100];
int i = 0;
scanf("%s",str);//读入字符串
while(str[i] != '\0')
{
if(str[i] >= 'a' && str[i] <= 'z')
str[i] = str[i] - 'a' + 'A';
i++;
}
if((fp = fopen("test.txt","w")) == NULL)
printf("can not open this file.\n");
fputs(str,fp); //字符串读写操作
fclose(fp); //关闭文件
}
4.编写一个递归函数,实现在已递增排序的整数数组中进行二分检索
答案参见2018级第三题
5.将满秩方阵n等价变换成一个上三角矩阵,(化为阶梯型)。
要求:以float a[N][N]作为函数deduce的唯一形参,且函数返回类型为void,编写函数deduce实现上述功能
#define N 3
void deduce(float a[N][N])
{
for(int i = 0; i < N - 1; i++) //共进行n-1行化简
{
for(int j = i + 1; j < N; j++) //第i+1行开始化简 一直化简到最后一行
{
float r = a[j][i] / a[i][i];
for(int k = i; k < N; k++) //对第j行的第k个元素开始化简
a[j][k] -= r*a[i][k];
}
}
}
6.每个学生信息卡片包括学生姓名和出生日期,从键盘依次输入若干学生信息,来创建一个用于管理学生信息的单向链表
①请给出该链表中各个结点的数据类型定义
②请编写程序,按照姓名的次序,依次插入每个学生信息,最后将链表中所有学生信息存入文本文件student.txt中
#include <malloc.h>
#include <string.h>
#include <stdio.h>
struct date{
int year,month,day;
};
struct card{
char name[20]; //姓名
struct date birth;
struct card* next;
};
void write(struct card* base) //文件操作
{
FILE* fp;
if((fp = fopen("student.txt","w")) == NULL)
printf("can not open file student.txt\n");
struct card*p = base;
while(p != NULL)
{
fprintf(fp,"%s\t%d %d %d\n",p -> name,p->birth.year,p->birth.month,p->birth.day);
p = p -> next;
}
fclose(fp);
}
int main()
{
int i;
struct card *head = (struct card*)malloc(sizeof(struct card));
head -> next = NULL;
struct card *pre = head, *p;
printf("1-continue to input 2-end \n");
scanf("%d",&i);
while(i == 1)
{
p = (struct card*)malloc(sizeof(struct card));
printf("please input the name\n");
scanf("%s",p -> name);
printf("please input the birthday\n");
scanf("%d %d %d",&(p->birth.year),&(p->birth.month),&(p->birth.day));
while(pre -> next != NULL && strcmp(p -> name, pre -> next -> name))
pre = pre -> next;
p -> next = pre -> next;
pre -> next = p;
pre = head;
printf("1-continue to input 2-end \n");
scanf("%d",&i);
}
struct card* base = head -> next;
write(base);
}
}```