C 2014年笔试题
1、指出程序中的错误,说明原因并修正#
1.1#
12345678int
*p,*q;
p=
malloc
(
sizeof
(
int
)*20);
q=
malloc
(
sizeof
(
int
)*10);
…
q=p;
…
free
(p);
free
(q);
分析:
错误1,q原本储存一片int类型的内存区域的地址,在没有释放这片地址时就修改了q的内容,使这片区域无法收回,导致内存泄漏。
错误2,p与q指向同一片内存区域,在使用free(p)后该内存区域已经释放,不能再free一遍。改正:将free(q)放在q=p前面(改正有多种说法,这里选择其中一种)
1.2#
12345678//交换字符串
void
swap(
char
*p,
char
*q)
{
char
*temp;
//p、q所指的值的交换
*temp=*p;
*p=*q;
*q=*temp;
}
分析:该代码首先创建了形参p和q接受两个char类型的地址,在代码内部交换的这两个形参的内容,没有对外界产生任何影响。
该代码的修改如下:
1234567void
swap(
char
*p,
char
*q)
{
char
temp[100];
strcpy
(temp,p);
//strcpy函数:复制字符串
strcpy
(p,q);
strcpy
(q,temp);
}
2、简答题#
2.1 arr为整型数组,N为数组长度,enumb为整型变量,下列函数负责找出arr数组中等于enumb的元素所在位置。指出程序的三种异常,并说明原因。#
12for
(i=N-1;arr[i]!=enumb;--i)
printf
(“%d”,i);
分析:
首先for循环后面应该有分号,否则每次循环都有输出。
其次如果arr数组中没有enumb,i就会变为负号,数组溢出。
最后,若i一直减小,i会减小直到溢出。
2.2 if(B) s1 else s2;是什么结构?使用显示结构语言该如何表示?并标出条件跳转和强制跳转#
分析:条件分支结构
1234if
(b)
goto
L1;
//条件跳转
goto
L2;
//强制跳转
L1: s1
L2: s2
2.3 C语言中,常量存储在哪里?静态局部变量和静态全局变量存储在哪里?#
分析:常量存储在常量区,静态局部变量和静态全局变量存储在全局数据区。
3填空题#
3.1 下面程序是对链表进行选择排序,填上空缺的部分#
1234567891011121314151617181920212223242526272829list selectsort(list head){
list p = (
struct
node*)
malloc
(
sizeof
(node));
p->next = head;
head = p;
//新建一个头结点
p = head->next;
list k = head, q = head;
while
(p->next)
{
q = p->next;
k = q;
//k记录最小值位置 //找到最小元素位置
while
(q) {
if
(q->data < k->data) {
k = q;
}
q = q->next;
}
//交换元素位置
if
(p->next != k) {
int
r = p->next->data;
p->next->data = k->data;
k->data = r;
}
p = p->next;
//填空一
}
p = head;
head = head->next;
//填空二
free
(p);
//释放头结点
return
head;
//填空三
}
3.2 快速排序法求某个数组前n个元素第k大的数#
12345678910111213141516171819202122int
find_k(
int
*a,
int
n,
int
k) {
int
i, j, t;
int
low = 0,high = n - 1;
do
{
i = low; j = high; t = a[low];
do
{
while
(a[j]>t) j--;
while
(a[i]<t) i++;
if
()
swap(&a[j], &a[i]);
else
;
}
while
(i<j);
if
(i == k)
return
t;
if
(i>k)
;
if
(i<k)
;
}
while
(low<high);
;
}
分析:该题目使用快排划分的第一种写法,原理是利用每次快排划分之后总能确定一个元素的最终位置。该程序可能仍然存在问题,最大的数字是第0个。
12345678910111213141516171819202122int
find_k(
int
*a,
int
n,
int
k) {
//从大到小排序
int
i, j, t;
int
low = 0,high = n - 1;
do
{
i = low; j = high; t = a[low];
do
{
while
(a[j]<t) j--;
while
(a[i]>t) i++;
if
(i<j)
swap(&a[j], &a[i]);
else
break
;
//填空1
}
while
(i<j);
if
(i == k)
return
t;
if
(i>k)
high = i - 1;
//填空2
if
(i<k)
low = i + 1;
//填空3
}
while
(low<high);
return
a[low];
//填空4
}
3.3约瑟夫环问题 【见2015年】 #
123456789101112131415161718192021222324int
a[N + 1];
int
*p = a, i,j,k;
for
(i = 0; i<N + 1; i++)
*(p+i) = i;
;
;
for
( i = 0; k != 1; p++)
{
if
()
p = a + 1;
if
()
i++;
if
()
{
k--;
i = 0;
*p = 0;
}
}
for
(i = 0; i<N + 1; i++)
{
if
()
printf
(
"%d\n"
,a[i]);
}
分析:与15年约瑟夫环区别
123456789101112131415161718192021222324int
a[N + 1];
int
*p = a, i,j,k;
//赋值0~N
for
(i = 0; i<N + 1; i++)
*(p+i) = i;
p = a + 1;
//填空1
k = N;
//填空2
for
( i = 0; k > 1; p++)
//k为剩下的人数
{
if
(p>a + N)
p = a + 1;
if
(*p != 0)
//碰到元素为0说明已经杀死,不参与计数
i++;
//i报数
if
(i == 3)
{
k--;
i = 0;
*p = 0;
}
}
//打印输出
for
(i = 0; i<N + 1; i++)
{
if
(a[i] != 0)
printf
(
"%d\n"
,a[i]);
}
3.4 完美乘法,若a*b=c,且abc中0~9的数字各出现一次,填写程序空缺处。#
1234567891011121314151617181920212223242526272829303132333435int
f[10],s[3];
int
n=0;
for
(
int
a = 12; a<999; a++)
{
int
t = 0;
//清空数字计数
for
(
int
x = 0; x<10; x++)
f[x] = 0;
for
(
int
b = 345; b<9999; b++)
{
int
c ;
;
//填空一
s[0] = a;
s[1] = b;
s[2] = c;
//计算abc中出现数字的次数
for
(
int
x = 0; x < 3; x++)
{
int
y = s[x];
while
()
{
int
t = y % 10;
f[t]++;
;
//填空二
}
}
//检查是否每个数都个出现一次
for
(
int
x = 0; x<10; x++)
{
if
() ;
//填空三
}
if
()
printf
(
"%d*%d=%d\n"
,a,b,c); ;
//填空四
}
}
分析:
1234567891011121314151617181920212223242526272829303132333435int
f[10],s[3];
int
n=0;
for
(
int
a = 12; a<999; a++)
{
int
t = 0;
//清空数字计数
for
(
int
x = 0; x<10; x++)
f[x] = 0;
for
(
int
b = 345; b<9999; b++)
{
int
c = a*b;
s[0] = a;
s[1] = b;
s[2] = c;
//计算abc中出现数字的次数
for
(
int
x = 0; x < 3; x++)
{
int
y = s[x];
while
(y > 0)
{
int
t = y % 10;
f[t]++;
y = y / 10;
}
}
//检查是否每个数都个出现一次
for
(
int
x = 0; x<10; x++)
{
if
(f[x] != 1) t++;
}
if
(t == 0)
printf
(
"%d*%d=%d\n"
,a,b,c);
n++;
//统计循环次数
}
}
4编程题#
4.1 将字符串逆转,函数原型void reverse(char *str);,要求空间复杂度为O(1)#
123456789101112131415161718192021#include <stdio.h>
#include <stdlib.h>
#include <string.h>
void
reverse(
char
*str)
{
int
i = 0, len =
strlen
(str);
for
(; i < len / 2; i++)
{
char
a = str[i];
str[i] = str[len - i - 1];
str[len - i - 1] = a;
}
}
int
main()
{
char
ch[] =
"helloworld"
;
reverse(ch);
printf
(
"逆转后:%s"
,ch);
return
0;
}
![]()
4.2 比较两个身份证字符串的生日大小。函数原型int isbothsame(char str1[19], char str2[19]);#
123456789101112131415161718#include <stdio.h>
#include <stdlib.h>
int
isbothsame(
char
str1[19],
char
str2[19])
{
int
low = 6, hight = 13;
while
(low<hight &&str1[low] == str2[low])low++;
//low记录不相同的位置
return
str1[low] - str2[low];
//负数表示str1的年长
}
int
main()
{
char
a[] =
"412824199605281234"
,b[] =
"41282519960825789x"
;
if
(isbothsame(a,b) < 0)
printf
(
"a年长!"
);
else
printf
(
"b年长!"
);
return
0;
}
4.3 计算1-x+x^2/2!-x^3/3!+…+x^n/n! 【见2015年】#
12345678910111213141516171819void
main()
{
int
n, x, j, i = 1;
float
sum = 1, k = -1;
printf
(
"Input n and x:\n"
);
scanf
(
"%d %d"
, &n, &x);
while
(i <= n) {
k = -1;
for
(j = 1; j <= i; j++) {
k = -1*k*x;
}
for
(j = 1; j <= i; j++) {
k = k/ j;
}
sum += k;
i++;
}
printf
(
"%f\n"
, sum);
}
动态规划改进:
12345678910111213void
main()
{
int
n,x,i=1;
float
sum = 1,k = -1;
printf
(
"Input n and x:\n"
);
scanf
(
"%d %d"
, &n, &x);
while
(i <= n) {
k = -1 * k*x / i;
sum += k;
i++;
}
printf
(
"%f"
, sum);
}
4.4一个链表,找出其中数据项最大的结点,然后将其移动到链表尾部(结点node由整型data和节点指针next构成),不允许申请新的结点#
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051#include <stdio.h>
#include <stdlib.h>
typedef
struct
slist
{
int
data;
struct
slist *next;
};
void
movemax(
struct
slist *L)
{
struct
slist *p = L->next, *pre = L, *max = p;
//找到最大值的位置
while
(p)
{
if
(p->data>max->data)max = p;
pre = p;
p = p->next;
}
//此时p指向NULL,pre指向最后一个结点
//最大值和最后一个节点交换
int
temp = pre->data;
pre->data = max->data;
max->data = temp;
}
int
main()
{
//建立单链表【尾插法】
int
a[] = {1,4,7,8,5,2,9,6,3};
struct
slist *p,*head = (
struct
slist*)
malloc
(
sizeof
(
struct
slist));
head ->next = NULL;
int
i;
p = head;
for
(i = 0;i < 9;i++)
{
struct
slist *node = (
struct
slist*)
malloc
(
sizeof
(
struct
slist));
node ->data = a[i];
node ->next = p ->next;
p ->next = node;
p = node;
}
printf
(
"找到最大值后移:\n"
);
movemax(head);
//输出
p = head ->next;
while
(p != NULL)
{
printf
(
"%d\t"
,p ->data);
p = p->next;
}
return
0;
}
作者:Hang Shao
出处:https://www.cnblogs.com/pam-sh/p/12585160.html
版权:本作品采用「知识共享」许可协议进行许可。
声明:欢迎交流! 原文链接 ,如有问题,可邮件(mir_soh@163.com)咨询.
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 理解Rust引用及其生命周期标识(上)
· 浏览器原生「磁吸」效果!Anchor Positioning 锚点定位神器解析
· DeepSeek 开源周回顾「GitHub 热点速览」
· 物流快递公司核心技术能力-地址解析分单基础技术分享
· .NET 10首个预览版发布:重大改进与新特性概览!
· AI与.NET技术实操系列(二):开始使用ML.NET
· .NET10 - 预览版1新功能体验(一)