面向对象C++编程与实践考试答案与解析

一、选择题(每题2分,共2×20=40分)

(1) 以下不能对数组 a 进行正确初始化的语句是( C )。
A. int a[2][3] = { 0 };
B. int a[ ][3] = { {0,1}, {0} };
C. int a[2][3] = { {0,1}, {2,3}, {4,5} };
D. int a[ ][3] = { 0, 1, 2, 3, 4, 5 };

【解析】

  • 选项A: 二维数组可以只对部分元素赋值。 int a[2][3] = { 0 }; 运行后,数组 a 的第一个元素被赋值为 0 ,而剩下的元素可默认被赋值为 0 ;即 int a[2][3] = { 0 }; 等价于 int a[2][3] = { {0,0,0}, {0,0,0} };
  • 选项B: 二维数组的一维下标可以不显式说明。即 int a[ ][3] = { {0, 1}, {0} }; 等价于 int a[2][3] = { {0, 1}, {0} }; 等价于 int a[2][3] = { {0, 1, 0}, {0, 0, 0} };
  • 选项C:int a[2][3] 为一个 2 行 3 列 的数组,而 { {0,1}, {2,3}, {4,5} }; 为 3 行 2 列,维度不匹配,初始化错误!
  • 选项D: 二维数组是按行存储的。 int a[ ][3] = { 0, 1, 2, 3, 4, 5 }; 等价于 int a[2][3] = { {0, 1, 2}, {3, 4, 5} };

(2) 用 const 声明的变量( C )。
A. 不能被读取
B. 在声明时可定义也可不定义
C. 只能被读取
D. 其值在程序中可以被改变

【解析】

符号常量 const 在使用之前一定要首先声明,并且要赋初值(定义),且在程序中不能改变其值。故选项 A、 B 、D 均错误。

(3) 有语句 int a[ ] = { 0, 2, 4, 6, 8, 10 },p = a + 1; 其值等于 0 的表达式是( D )。
A. * (p++)
B.
(++p)
C. (p–)
D.
(–p)

【解析】

首先是数组+1的问题。在 C++ 中,一个数组 a ,其中 a 既表示数组名,同时也是数组的首地址,指向数组的第一个元素。而 a + 1 就是将 a 的值(地址)加上单个数组元素个长度(这里是一个 int 的长度),所以 a + 1 指向了第二个元素,即 a[1]。所以 p = a + 1; 等价于 p = & a[1]; 也就是说*p 的值等于 2 。

然后就是前置(后置)自增(自减)的问题。以自增为例,假设 i = 1;那么:

  • a = i++;相当于 a = i; i++; 此时 a = 1,i = 2;
  • a = ++i;相当于 i++; a = i; 此时 i = 2, a = 2;

最后就是指针的加减问题。选项 A ~ D 形如 *(x),则:

  • 选项 A,x = p++ 相当于 x=p; p = p+1; ⇒ (p++) = (p) = & a[1]; ⇒ 值等于 2
  • 选项 B,x = ++p 相当于 p = p+1; x=p; ⇒ (++p) = (p+1) = & a[2]; ⇒ 值等于 4
  • 选项 C,x = p– 相当于 x=p; p = p-1; ⇒ (p–) = (p) = & a[1]; ⇒ 值等于 2
  • 选项 D,x = –p 相当于 p = p-1; x=p; ⇒ (++p) = (p-1) = & a[0]; ⇒ 值等于 0

(4) 下列的描述中( C )是错误的。
A. 使用全局变量可以从被调用函数中获取多个操作结果
B. 局部变量可以初始化,若不初始化,则系统默认它的值为 0
C. 当函数调用完后,静态局部变量的值不会消失
D. 全局变量若不初始化,则系统默认它的值为 0

【解析】

首先是关于局部变量和全局变量初始化的问题。全局变量不初始化,系统是会默认为它赋值为 0 的 ;而局部变量不初始化,系统会默认为它赋值一个随机的值。故 B 和 D 正确。

然后是局部变量和全局变量使用的问题。全局变量在的生存期是从其被定义到程序运行结束的,其间,它的值可以被任何函数调用或修改,所以 A 是正确的。静态局部变量即定义为static的局部变量,这个静态局部变量的值在函数调用完后,其所占用的内存是不会被释放的,即它在程序结束前是一直占据这个内存而不会消失的,自然其内的值也就不会消失了,而如果不是静态局部变量 ,而只是普通的变量的话,在函数调用完后,它所占据的内存将会被释放,那么这个值也就没了,即消失。所以 C 是错误的。

(5) C++ 语言的跳转语句中,对于 break 和 continue 说法正确的是( B )。
A. break 语句只能用于循环体中
B. continue 语句只能用于循环体中
C. break 是无条件跳转语句,continue 不是
D. break 和 continue 的跳转范围不够明确,容易产生问题

【解析】

break 语句可以用于 switch 或循环体内,作用是跳出 switch 或循环体。continue 语句只能用于循环体内,作用是结束当前循环,进入下次循环。因此这两种语句跳转范围很清晰,并且都是需要判断的(即需要 if 语句)。所以选 B 。

(6) S 是字符数组,用于存储字符串,下面不能够判断字符串 S 是空串的是( A )。
A. if (S[0] == 0 )
B. if (strlen(S) == 0)
C. if (strcmp(S, “”) == 0)
D. if (S == ‘\0’)

【解析】

字符串数组为空时,strlen 长度为 0,与空字符”” 比较 strcmp 返回 0 ,字符串数组里仅有 “\0” 一个元素。所以 B、C、D 全对,A 错误。

(7) C++ 函数的参数传递方式有( D )。
A. 地址传递
B. 引用传递
C. 双向值传递
D. 由用户指定传递方式

【解析】

函数的参数传递有很多种方式,具体有:

  • 值传递:例如 void func(int x, int y)
  • 地址传递(指针):例如 void func(int x, int y)
  • 引用传递:例如 void func(int &x, int &y)

因此传递方式可以根据实际需求由用户指定任意一种即可。故选 D 。

(8) 下面判断是否构成重载函数的条件中,错误的判断条件是( D )。
A. 参数类型不同
B. 参数个数不同
C. 参数顺序不同
D. 函数返回值不同

【解析】

所谓函数重载,就是指同样的函数名的情况下,其形参的个数、类型、顺序不同,而函数返回值不同则不属于定义范围。故选 D 。

(9) 设 a 和 b 是两个结构体变量,下面正确的表达式是( A )。
A. a = b
B. a = b + 1
C. a > b
D. a == b

【解析】

结构体变量只能进行两种运算: 整体引用(赋值,参数传递) 或访问成员(点运算—地址方式简化,地址方式)。其中 选项 A 即为整体引用中的赋值操作。

(10) 派生类对象只能访问基类中的( A )。
A. 公有继承的公有成员
B. 公有继承的私有成员
C. 公有继承的保护成员
D. 私有继承的公有成员

【解析】

根据类的继承关系定义:

当类的继承方式为公有继承时,基类的公有成员和保护成员的访问属性在派生类中不变,而基类的私有成员不可直接访问。也就是说基类的公有成员和保护成员被集成到派生类中访问属性不变,仍作为派生类的公有成员和保护成员,派生类的其他成员可以直接访问它们。在类族之外只能通过派生类的对象访问从基类继承的公有成员。而无论是派生类的成员还是派生类的对象都无法直接访问基类的私有成员。

当类的继承方式为私有继承时,基类中的公有成员和保护成员都以私有成员身份出现在派生类中,而基类的私有成员在派生类中不可直接访问。也就是说基类的公有成员和保护成员被继承后作为派生类的私有成员,派生类的其他成员可以直接访问它们,但是在类族外部通过派生类的对象无法直接访问它们。无论是派生类的成员还是派生类的对象,都无法直接访问从基类继承的私有成员。

综上,本题选 A 。

(11) 关于构造函数的叙述中,错误的说法是( B )。
A. 构造函数的名称必须为类名
B. 构造函数最多只能有一个
C. 创建对象时自动执行构造函数
D. 构造函数无任何函数类型

【解析】

根据构造函数的定义,构造函数的函数名与类名相同,并且没有返回值,也就不存在函数类型。构造函数在对象被创建的时候将被自动调用。因此 A、C、D 均对。对于选项 B,构造函数也是可以重载的,因此可以存在多个构造函数,选项 B 错误。

(12) ( A )只能访问静态成员变量。
A. 静态成员函数
B. 虚函数
C. 构造函数
D. 析构函数

【解析】

静态成员函数内部只能访问静态成员变量/函数,不能访问非静态成员变量/函数。因为非静态成员变量/函数在创建对象的时候才存在。而静态成员可以直接通过类调用,可能压根没有对象。故选 A 。

(13) C++ 中类有两种用法,一种是类的实例化,即生成类对象;另一种是通过( B )派生出新的类。
A. 复用
B. 继承
C. 重载
D. 封装

【解析】类的用法即实例化和继承。选 B 。

(14) 下面描述中,正确的是( D )。
A. 虚函数是没有实现的函数
B. 纯虚函数的实现在派生类定义
C. 抽象类是具有纯虚函数的类
D. 抽象类指针可以指向不同的派生类

【解析】

选项 A, 错误,纯虚函数才是没有实现的函数
选项 B,错误,纯虚函数在基类中不可以给出具体实现
选项 C,错误, 抽象类是有纯虚函数的类
选项 D,正确。

(15) 一个类的友函数能够访问该类的( D )。
A. 私有成员
B. 保护成员
C. 公有成员
D. 所有成员

【解析】

类的友函数与其他成员函数一样,对类内的所有成员都具有访问权限。故选 D 。

(16) 下列关于构造函数说法不正确的是( C )。
A. 构造函数必须与类同名
B. 构造函数可以省略不写
C. 构造函数必须有返回值
D. 在构造函数中可以对类中的成员进行初始化

【解析】

根据构造函数的定义,构造函数的函数名与类名相同,并且没有返回值,也就不存在函数类型。构造函数在对象被创建的时候将被自动调用。构造函数可以访问类中所有成员,因此可以承担初始化的功能。故选 C 。

(17) 关于 new 运算符的下列描述中,( D )是错误的。
A. 它可以用来动态创建对象和对象数组
B. 使用它创建对象或对象数组,可以使用 delete 删除
C. 使用它创建对象时要调用构造函数
D. 使用它调用对象数组时不许指定初始值

【解析】

建立和删除堆对象(对象或对象数组),使用 new 和 delete,二者刚好对应于构造函数和析构函数。在调用对象数组时,必须指定初始值,故 D 错误。

(18) 建立包含有类对象成员的派生类对象时,自动调用构造函数的执行顺序依次为( D )的构造函数。
A. 基类、自己所属类、成员对象成员所属类
B. 对象成员所属类、基类、自己所属类
C. 自己所属类、对象成员所属类、基类
D. 基类、对象成员所属类、自己所属类

【解析】

派生类构造函数执行的一般次序如下。

根据以上定义,选择 D 。

(19) 下列说法正确的是( B )。
A. 内联函数在运行时是将该函数的目标代码插入每个调用该函数的地方
B. 内联函数在编译时是将该函数的目标代码插入每个调用该函数的地方
C. 类的内联函数必须在类体内定义
D. 类的内联函数必须在类体外通过关键字 inline 定义

【解析】

内联函数不是在调用时发生控制转移,而是在编译时将函数体嵌入在每一个调用的地方。类的内联函数既可以在类体内定义(隐式声明,不使用 inline)也可以在类体外定义(显示声明,使用 inline),没有硬性规定。故选 B 。

(20) 执行语句:

int a = 10, b;
int &pa = a, &pb = b;

后,下列正确的语句是( B )。
A. &pb = a
B. pb = pa
C. &pb = &pa
D. pb = pa

【解析】

引用相当于变量的别名,对引用的操作与对变量直接操作完全一样。对变量赋值,语法合理,选项 B 正确。

引用声明完毕后,相当于目标变量名有两个名称,即该目标原名称和引用名,且不能再把该引用名作为其他变量名的别名。故 A 和 C 错误。

二、判断题(每题 1 分,共10×1 =10分)

(1) 函数的形参是局部变量。( √ )

【解析】形参只在函数内起作用,属于局部变量。

(2) 有语句 #define n 10 ,则 int a[n] ; 定义数组是合法的。( √ )

【解析】#define 的功能是将标识符定义为其后的常量。一经定义,程序中就可以直接用标识符来表示这个常量。千万不要在 #define 语句末尾加分号”;” 否则后续的数组定义则不合法。

(3) 赋值运算符只能作为成员函数进行重载。( × )

【解析】C++规定=,[ ],(),->这四个运算符只能被重载为类的非静态成员函数。

(4) 条件编译的作用是根据不同条件进行编译不同程序段,以提高程序的兼容性。( √ )

【解析】条件编译就是让程序段在满足一定的条件后才参与到程序编译中,因此可以使得同一个源程序产生不同的目标代码,兼容性被提高。

(5) 静态数据成员必须在类外定义和初始化。( × )

【解析】在C++中,类的静态成员(static member)必须在类内声明,在类外初始化。因为静态成员属于整个类,而不属于某个对象,如果在类内初始化,会导致每个对象都包含该静态成员,这是矛盾的。

(6) 可以对类成员变量直接赋值。( × )

(7) 在 class 定义一个类时,数据成员函数的默认访问权限是私有的。( √ )

(8) 抽象类通常应用派生类。( √ )

【解析】抽象类不能够实例化,因此通常需要派生类。

(9) 指针可以做任何类型的强制转换。( √ )

(10) 对象不能作为数组元素。( × )

【解析】数组的元素不仅可以是基本数据类型,也可以是自定义类型,类对象也是可以作为数组元素的。

三、编程题

1、编写程序,输入 100 个数值,从小到大排序后输出。(10分)

【解析】采用冒泡排序法即可。

#include
using namespace std;
int main()
{
    int n, i, j, t, a[100];
    cin >> n;
    for (i = 0; i < n; i++)
        cin >> a[i];
    for (i = 0; i < n - 1; i++)
        for (j = 0; j < n - 1 - i; j++)
            if (a[j] > a[j + 1])
            {
                t = a[j];
                a[j] = a[j + 1];
                a[j + 1] = t;
            }
    for (i = 0; i < n; i++)
        cout << a[i] << " ";
    cout << endl;
    return 0;
}

2、输入一行字符,按输入字符的反序建立一个单向链表存储这些字符,并输出该链表中的字符。(10分)
节点的结构:

struct node{
    char ch;
    node *next;
};
#include
using namespace std;
struct node
{
    char ch;
    node *next;
};
void show(node *head);
int main()
{
    node *head, *p;
    char c;
    head = NULL;
    while ((c = getchar()) != '\n') //输入一行字符
    {
        p = new node; //建立新结点
        p->ch = c;
        p->next = head; //插入表头
        head = p;
    }
    show(head);
}
void show(node *head) //输出链表
{
    node *p = head;
    cout << "链表中的字符是: \n";
    while (p)
    {
        cout << p->ch;
        p = p->next;
    }
    cout << endl;
}

3、设计三角形类 CTriangle ,写出下面 6 个成员函数。三角形类的部分定义如下:(30分)

class CTriangle{
    float a, b, c;  //三角形的三条边长
    float area;  //保存三角形的面积
    public:
        // (1)默认构造函数
        // (2)有初始值的构造函数
        // (3)拷贝函数
        // (4)设置三角形的三条边长度
        // (5)得到三角形的三条边长度
        // (6)"+" 运算符重载,实现 2 个三角形的面积之和
};
#include
#include
#include
using namespace std;

class CTriangle {
    float a, b, c;  //三角形的三条边长
    float area;  //保存三角形的面积
public:

    // (1)默认构造函数
    CTriangle(){};

    // (2)有初始值的构造函数
    CTriangle(float x, float y, float z);

    // (3)拷贝函数
    CTriangle(CTriangle &t);

    // (4)设置三角形的三条边长度
    void Set(char point, float val);

    // (5)得到三角形的三条边长度
    float Get(char point);

    // (6)"+" 运算符重载,实现 2 个三角形的面积之和
    friend float operator+(CTriangle t1, CTriangle t2);
};

CTriangle::CTriangle(float x = 1, float y = 1, float z = 1) {
    a = x;
    b = y;
    c = z;
    float p = (a + b + c) / 2;
    area = sqrt(p * (p - a) * (p - b) * (p - c));
}

CTriangle::CTriangle(CTriangle &t) {
    a = t.a;
    b = t.b;
    c = t.c;
    area = t.area;
}

void CTriangle::Set(char point, float val) {
    if (point == 'a') {
        a = val;
    }
    else if (point == 'b') {
        b = val;
    }
    else if (point == 'c') {
        c = val;
    }else{
        cout << "设置错误!"<

Original: https://www.cnblogs.com/gshang/p/15746177.html
Author: GShang
Title: 面向对象C++编程与实践考试答案与解析

原创文章受到原创版权保护。转载请注明出处:https://www.johngo689.com/536403/

转载文章受原作者版权保护。转载请注明原作者出处!

(0)

大家都在看

  • Delphi XE8,C++ Builder XE8,RAD Studio XE8 官方 ISO 文件下载,附激活工具

    RAD Studio XE8 v22.0.19027.8951 官方ISO下载(6.72G):http://altd.embarcadero.com/download/radstu…

    C++ 2023年5月29日
    077
  • [C++] 左值、右值、右值引用

    lvalue 代表了对象,可通过取地址符获取地址,可赋值。L 可看做 location。 rvalue 代表了数据,不能获取内存地址,不可赋值。 rvalue 不能当做 lvalu…

    C++ 2023年5月29日
    050
  • 转:TinyXM–优秀的C++ XML解析器

    include include “tinyxml.h” include “tinystr.h” include include in…

    C++ 2023年5月29日
    047
  • C++中 线程函数为静态函数 及 类成员函数作为回调函数

    线程函数为静态函数: 线程控制函数和是不是静态函数没关系,静态函数是在构造中分配的地址空间,只有在析构时才释放也就是全局的东西,不管线程是否运行,静态函数的地址是不变的,并不在线程…

    C++ 2023年5月29日
    062
  • c++智能指针

    跟comptr类似 明确定义AddRef和Release,然后定义与comptr类似的一个辅助类. 这里有2种方式 1.Release的时候引用计数为0的时候删除对象 2.定义一个…

    C++ 2023年5月29日
    094
  • C++ d-bus 使用实例

    因为以后工作用的到D-bus,这两天抽空看了下c++下得d-bus的使用方法。因为网上对c++下得d-bus使用说明几乎没有,所以,在这里记录下以供同仁使用。同时感谢shengpe…

    C++ 2023年5月29日
    060
  • C++实现图的遍历和最短路径

    摘自:https://blog.csdn.net/qq_45694646/article/details/106764026 C++实现图的基本操作 数据结构之图(存储,遍历,最短…

    C++ 2023年5月29日
    070
  • C++ *和&

    概述 在c++中,当申明变量int *p 的时,表示p是一个储存地址的变量;比如int _p=0,表示p指向地址为00000000的地址单元。当申明指针p之后,再用_p表示p指向的…

    C++ 2023年5月29日
    058
  • (转载)C++lambda表达式

    C++ 语言中的lambda表达式在很多情况下提供了函数对象的另一种实现机制。Lambda表达式并不是STL所特有的,但它广泛应用于这一环境中。Lambda是表达式是定义一个没有名…

    C++ 2023年5月29日
    067
  • Android JNI c/c++调用java 无需新建虚拟机

    近期通过研究SDL源码 得出android JNI c/c++调用java 无需新建虚拟机: 具体步骤如下 第一步获得:两个参数 JNIEnv和jclass void Java_c…

    C++ 2023年5月29日
    045
  • C++ CRTP

    CRTP 英:The curiously recurring template pattern (CRTP) is a C++ idiom in which a class X d…

    C++ 2023年5月29日
    088
  • c++实践课(上课用)

    源程序: //编写一个程序,将从键盘输入的n个字符串保存在一个一维数组A中。在输入字符串之前,先输入n的值。//要求,数组A需要动态申请空间,程序运行结束前再释放掉。//再输出n字…

    C++ 2023年5月29日
    043
  • c++ effective总结(一)

    条款一:视c++为一个语言联邦 c++可以认为是由C,Object-Oriented C++(面向对象),Template C++(模板),STL(c++标准模板库)四种次语言组成…

    C++ 2023年5月29日
    080
  • Windows 8 添加隐私策略(C++版)

    well.新年上班第一天.不幸收到MS官方针对我们Snack Cards应用程序被打回消息.看看Report 内容如下: The app has declared access t…

    C++ 2023年5月29日
    060
  • dev c++ 无法单步调试

    遇到cout语句中有endl时,点击下一步无反应,需将endl改为’\n’ 或直接添加 #define endl ‘\n’ 替换qt…

    C++ 2023年5月29日
    050
  • C++匿名函数-Lambda表达式

    为什么存在匿名函数 使用 STL 时,往往会大量用到函数对象,为此要编写很多函数对象类。有的函数对象类只用来定义了一个对象,而且这个对象也只使用了一次,编写这样的函数对象类就有点浪…

    C++ 2023年5月29日
    063
亲爱的 Coder【最近整理,可免费获取】👉 最新必读书单  | 👏 面试题下载  | 🌎 免费的AI知识星球