文章目录
1
测试代码:
#include <iostream>
int main() {
std::cout << "int *p1 = new int[10]; \n";
int *p1 = new int[10];
for(int i=0;i<10;i++)
{
std::cout << p1[i] << "\t";
}
std::cout << "\nint *p1 = new int[10]; \n";
int *p2 = new int[10]();
for(int i=0;i<10;i++)
{
std::cout << p2[i] << "\t";
}
return 0;
}
2
测试代码:
#include <iostream>
#include <ctime>
using namespace std;
void knuth(int n, int m)
{
srand((unsigned int)time(0));
cout << "rand()产生随机数范围为0到"<< RAND_MAX;
for (int i = 0; i < n; i++) {
if (rand()%(n-i)<=m) {
cout << i << endl;
m--;
}
}
}
int main() {
knuth(10000,1);
return 0;
}
3
测试代码:
#include <iostream>
using namespace std;
void prim(int m, int n)
{
if (m >= n)
{
while (m%n) n++;
m/=n;
prim(m, n);
cout << n << endl;
}
}
int main() {
prim(10,2);
return 0;
}
4
测试代码:
#include <iostream>
using namespace std;
void fun()
{
enum string{
x1,
x2,
x3=10,
x4,
x5,
} x;
cout << "x=" << x;
}
int main() {
fun();
return 0;
}
5
解析:
{ char每次移动1个字节;short移动2个字节 ;int , long ,float移动4个字节 ;double移动8个字节}
6
解析:
这题的正确答案应该是32位系统是4 64位系统是8,数组作为函数的参数是会退化为函数指针的,想想看,数组作为函数参数的时候经常是需要传递数组大小的。
7 下面关于虚函数和函数重载的叙述不正确的是(A)
解释:
虚函数也是类的成员函数,A说法是不正确的;
8 处理a.html文件时,以下哪行伪代码可能导致内存越界或者抛出异常(B)
int totalBlank = 0;
int blankNum = 0;
int taglen = page.taglst.size();
A for(int i = 1; i < taglen-1; ++i)
{
//check blank
B while(page.taglst[i] == "<br>" && i < taglen)
{
C ++totalBlank;
D ++i;
}
E if(totalBlank > 10)
F blankNum += totalBlank;
G totalBlank = 0;
}
注意:以上代码中taglen是html文件中存在元素的个数,a.html中taglen的值是15,page.taglst[i]取的是a.html中的元素,例如page.taglst[1]的值是
a.html的文件如下:
<html>
<title>test</title>
<body>
<div>aaaaaaa</div>
</body>
</html>
<br>
<br>
<br>
<br>
<br>
9
解释:
str是复合类型数组char[6],维度6是其类型的一部分,sizeof取其 维度*sizeof(char),故为6;
strlen 求c类型string 的长度,不含尾部的’\0’,故为5;
p只是个指针,32位机上为4;
c++中不允许隐式的数组拷贝,所以Func的参数会被隐式地转为char*,故为4;
note:若Func的原型为void Func(char (&str_arg) [6])(若不为6则调用出错),则结果为6.
10
解释:
该题的关键是要认清楚强制类型转换后指针的类型。
p的类型为char *,p++后p指向str数组的第2个元素即字母“l”的位置。
p1的类型为int *,p1++后p1指向的位置增加4个字节,指向str数组中的第6个元素即字母“t”的位置。
因此最后p的内容为“to test something”。
11
解释:
这道题主要考察的知识点是 :全局变量,静态局部变量,局部变量空间的堆分配和栈分配
其中全局变量和静态局部变量时从 静态存储区中划分的空间,
二者的区别在于作用域的不同,全局变量作用域大于静态局部变量(只用于声明它的函数中),
而之所以是先释放 D 在释放 C的原因是, 程序中首先调用的是 C的构造函数,然后调用的是 D 的构造函数,析构函数的调用与构造函数的调用顺序刚好相反。
局部变量A 是通过 new 从系统的堆空间中分配的,程序运行结束之后,系统是不会自动回收分配给它的空间的,需要程序员手动调用 delete 来释放。
局部变量 B 对象的空间来自于系统的栈空间,在该方法执行结束就会由系统自动通过调用析构方法将其空间释放。
之所以是 先 A 后 B 是因为,B 是在函数执行到 结尾 “}” 的时候才调用析构函数, 而语句 delete a ; 位于函数结尾 “}” 之前。
12
解释:
考察点:c++ 类的内存布局。
上精华图:一张图说明类中成员变量,成员函数,静态变量与函数的空间位置。
13
解释:
方法重载的返回值的类型可以不同,因为判断方法重载的方法主要是根据方法的参数不同来判定;
方法重写的返回值类型需要相同,重写就是子类继承了父类的方法,并在此方法上重写属于自己的特征,既然是继承过来的,那么它的返回值类型就必须要相同
方法重载(overload):
1.必须是同一个类
2方法名(也可以叫函数)一样
3参数类型不一样或参数数量不一样
**方法的重写(override)**两同两小一大原则:
方法名相同,参数类型相同
子类返回类型小于等于父类方法返回类型,
子类抛出异常小于等于父类方法抛出异常,
子类访问权限大于等于父类方法访问权限。
14
#include <iostream>
#include <cstring>
using namespace std;
#define M 5
#define N 20
int fun(char(* ss)[N], int *n)
{
int i, k = 0, len = N;
for (i = 0; i < M; i++)
{
len = strlen(ss[i]);
// 把第一个字符串长度赋值给*n
if (i == 0)
*n = len;
// 如果新来的len比*n小,则重新赋值*n
// 并找出下标i,复制给k
if (len < * n)
{
*n = len;
k = i;
}
}
return k;
}
int main() {
char ss[M][N] = {"shanghai", "guangzhou", "beijing", "tianjing", "chongqing"};
int n, k, i;
printf("\nThe originalb stringsare:\n");
for (i = 0; i < M; i++)
puts(ss[i]);
k = fun(ss, &n);
printf("\nThe length of shortest string is: % d\n", n);
printf("\nThe shortest string is: % s\n", ss[k]);
return 0;
}
解释:
puts() 就是输出
15 写出下面程序的输出结果
# include <iostream>
class A
{
public:
void FuncA()
{
printf( "FuncA called\n" );
}
virtual void FuncB()
{
printf( "FuncB called\n" );
}
};
class B : public A
{
public:
void FuncA()
{
A::FuncA();
printf( "FuncAB called\n" );
}
virtual void FuncB()
{
printf( "FuncBB called\n" );
}
};
int main()
{
B b;
A *pa;
pa = &b;
A *pa2 = new A;
pa->FuncA(); // pa=&b动态绑定但是FuncA不是虚函数,所以FuncA called
pa->FuncB(); // FuncB是虚函数所以调用B中FuncB,FuncBB called
pa2->FuncA(); // pa2是指向A,不涉及虚函数,调用的都是A中函数,所以FuncA called
pa2->FuncB(); // FuncB called
delete pa2;
}
程序云型结果:
16
In the main() function, after ModifyString(text) is called, what’s the value of ‘text’?
int FindSubString( char* pch )
{
int count = 0;
char * p1 = pch;
while ( *p1 != '\0' )
{
if ( *p1 == p1[1] - 1 )
{
p1++;
count++;
}else {
break;
}
}
int count2 = count;
while ( *p1 != '\0' )
{
if ( *p1 == p1[1] + 1 )
{
p1++;
count2--;
}else {
break;
}
}
if ( count2 == 0 )
return(count);
return(0);
}
void ModifyString( char* pText )
{
char * p1 = pText;
char * p2 = p1;
while ( *p1 != '\0' )
{
int count = FindSubString( p1 );
if ( count > 0 )
{
*p2++ = *p1;
sprintf( p2, "%i", count );
while ( *p2 != '\0' )
{
p2++;
}
p1 += count + count + 1;
}else {
*p2++ = *p1++;
}
}
}
void main( void )
{
char text[32] = "XYBCDCBABABA";
ModifyString( text );
printf( text );
}
解释:
有点难,有时间回来再看
17
解释:
难啊,回来再看
18
解释:
auto int 表示的是局部变量,在我们声明局部变量,或者函数参数,可以加上这个关键字,表明是分配在堆栈中
本程序中的变量b声明为static静态全局变量,所以它的作用域是全局作用域,每次调用sum函数都会累加2
19
#include<iostream>
using namespace std;
class MyClass
{
public:
MyClass(int i = 0)
{
cout << i;
}
MyClass(const MyClass &x)
{
cout << 2;
}
MyClass &operator=(const MyClass &x)
{
cout << 3;
return *this;
}
~MyClass()
{
cout << 4;
}
};
int main()
{
MyClass obj1(1), obj2(2);
MyClass obj3 = obj1;
return 0;
}
运行时的输出结果是(C)
解析:
C D 辨析:
关键是区分 浅/深拷贝操作 和 赋值操作:
没有重载=之前:
A a ;
A b;
a = b;
这里是赋值操作。
A a;
A b = a;
这里是浅拷贝操作。
重载 = 之后:
A a ;
A b;
a = b;
这里是深拷贝操作(当然这道题直接返回了,通常我们重载赋值运算符进行深拷贝操作)。
A a;
A b = a;
这里还是浅拷贝操作。
所以 MyClass obj3 = obj1; 调用的是拷贝构造函数。
如果写成 MyClass obj3; obj3 = obj1; 输出的结果就是 1203444
20
解释:
函数char *myString()中没有使用new或者malloc分配内存,所有buffer数组的内存区域在栈区
随着char *myString()的结束,栈区内存释放,字符数组也就不存在了,所以会产生野指针,输出结果未知