Тест

Набор задач 1

Изучите следующую программу, а затем ответьте на вопросы ниже. Мы бы хотели, чтобы вы отвечали на вопросы, просматривая только исходный код, т.е. не копируйте его в файл, не компилируйте и отвечайте на вопросы, основываясь на его запуске. Это лишит вас всего удовольствия!

int main() {
  int counter, first, last, next;
  first = 1; last = 2;

  for (counter = first; counter <= last; counter++) {
    cout << "\n " << counter;
    next = counter * counter;
    cout << " " << next;
  }

  counter = first;
  while (counter <= last) {
    cout << "\n " << counter;
    next = counter * counter;
    cout << " " << next;
    counter++;
  }

  counter = first;
  do {
    cout << "\n " << counter;
    next = counter * counter;
    cout << " " << next;
    counter++;
  } while (counter < last);
}

Вопрос 1: Каков результат этой программы?

А) 1 2
2 4
1 2
2 4
1 2
2 4
Б) 1 1
2 4
1 1
2 4
1 1
2 4
С) 1 1
2 4
1 1
2 4
1 1
Д) 1 1
2 4
1 1
1 1
2 4
Е) Ничего не выводит - есть ошибки в синтаксисе.

Вопрос 2. Что произойдет, если мы удалим инициализацию «счетчика» перед циклом do- while?

А) Бесконечный цикл — цикл do- while выводит серию единиц.
Б) Вывод программы не изменится
С) Цикл do- while выводит 2 и 4.
Д) Цикл do- while ничего не выводит
Е) Цикл do- while выводит 3 и 9.

Вопрос 3. Учитывая исходную программу вверху этой страницы, предположим, что мы удалили строку, которая инициализирует переменную счетчика перед циклом while. Что произойдет, если мы также удалим строку counter++ внутри цикла while, как показано ниже?

А) Цикл while ничего не выводит.
Б) Цикл while выводит 1 и 1; цикл do- while ничего не выводит.
С) Вывод цикла while такой же, как и при включении обеих строк.
Д) Система будет выводить случайные числа, пока мы не выключим компьютер.
Е) Цикл while — это бесконечный цикл.

Вопрос 4. Учитывая исходную программу вверху этой страницы, что произойдет, если цикл while будет выглядеть так?

counter = first;
while (counter <= last) {
  cout << "\n" << counter;
  if (first % 2 == 0)
    next = counter * counter;
  cout << "  " << next;
  counter++;
}
А) Вывод цикла while такой же, как и в исходной программе.
Б) Цикл while ничего не выводит
С) Выходные данные цикла while — 1 1 и 1 4.
Д) Выходные данные цикла while — 1 2 и 2 4.
Е) Выходные данные цикла while — 1 4 и 2 4.
Ф) Выходные данные цикла while — 2 4 и 2 4.

Вопрос 5: Что произойдет, если первая переменная больше последней?

А) Цикл while выведет что-то, но больше ничего.
Б) Цикл do while выведет что-то, но больше ничего.
С) Выхода не будет вообще.
Д) Программа выдаст ошибку или вылетит
Е) Цикл for выведет что-то, но больше ничего.

Вопрос 6. Что выведет программа, если мы инициализируем первую переменную такой же, как и последнюю переменную?

А) Цикл do while выведет что-то, но больше ничего.
Б) Цикл while выведет что-то, но больше ничего.
С) Каждый цикл выводит одну строку.
Д) Цикл do while выведет 2 строки, а другой — одну строку.
Е) Он ничего не выведет
Ф) Цикл for выведет что-то, но больше ничего.


Набор задач 2

Как и в предыдущем наборе задач, вашему вниманию предлагается программа. Пожалуйста, ответьте на следующие вопросы, просматривая только исходный код.

#include <iostream>
using namespace std;

int main() {
  int Boys = 3, Girls = 5;
  void F1(int males, int females);
  void F2(int &m, int &f);

  F1(Boys, Girls);
  cout << "\nAfter calling F1, within main()";
  cout << "\n\tBoys = " << Boys; // #2
  cout << "\n\tGirls = " << Girls;

  F2(Boys, Girls);
  cout << "\nAfter calling F2, within main()";
  cout << "\n\tBoys = " << Boys; // #4
  cout << "\n\tGirls = " << Girls;
}

void F1(int b, int g) {
  b += 3, g += 4;
  cout << "\nF1";
  cout << "\n\tBoys = " << b; // #1
  cout << "\n\tGirls = " << g;
}

void F2(int &b, int &g) {
  b = b + 8, g = g + 5;
  cout << "\nF2";
  cout << "\n\tBoys = " << b; // #3
  cout << "\n\tGirls = " << g;
}

Вопрос 1. Каковы выходные данные переменной Boys в отмеченных строках?

А) №1: 6
№2: 3
№3: 11
№ 4: 11
Б) №1: 6
№2: 3
№3: 11
№ 4: 3
С) №1: 6
№ 2: 6
№3: 11
№ 4: 11
Д) Он ничего не выводит, потому что не компилируется и не запускается.

Вопрос 2: Выберите все, что относится к следующим строкам программы:

void F1(int males, int females);
void F2(int &m, int &f);
А) Правила C++ гласят, что мы можем удалить эти две строки, если методы определены перед использованием.
Б) Правила C++ гласят, что имена аргументов в объявлении и определении должны быть одинаковыми.
С) Эта программа выйдет из строя, если мы удалим эти две строки.
Д) Чаще всего объявления указываются в глобальной области видимости.
Е) Это так называемые предварительные объявления.

Вопрос 3: Если мы переместим следующую строку из main() и поместим ее в глобальную область видимости, что произойдет?

int Boys = 3, Girls = 5;
А) Результат будет таким же.
Б) Мальчики = 3, а девочки = 5 во всех выходных данных.
С) Мальчики = 3, а девочки = 5 только в выводе функции main().

Вопрос 4: Что, если мы изменим начало программы так:

// We have moved moved these to global scope
const int Boys = 3;
const int Girls = 5;

void main() {
  //int Boys = 3, Girls = 5;
А) Программа скомпилируется, но вылетит при попытке запустить ее.
Б) Никаких изменений в выводе не будет
С) Результатом будет: Мальчики = 3 Девочки = 5 на протяжении всей программы.
Д) Результатом будет Boys = 3 Girls = 5 только в выводе main().
Е) Программа, вероятно, не скомпилируется (в зависимости от компилятора).

Вопрос 5: Данные передаются по значению в F2.

А) Истинный.
Б) ЛОЖЬ.


Набор задач 3

Как и в предыдущем наборе задач, вашему вниманию предлагается программа. Пожалуйста, ответьте на следующие вопросы, просматривая только исходный код. Этот более интересен, чем два предыдущих — внимательно проследите за кодом.

#include <iostream>
using namespace std;

const int MAX_SIZE = 20;
typedef int ARR2D[MAX_SIZE][MAX_SIZE];

void Print(ARR2D in_array, int rows, int cols);
void Fill(ARR2D in_array, int rows, int cols);

int main() {
  ARR2D matrix;
  int row, col;
  do {
    cout << "Please enter the size of the matrix to generate (rows and cols) :" << endl;
    cin >> row >> col;
  } while (row <= 0 || row > MAX_SIZE || col <= 0 || col > MAX_SIZE);
  Fill(matrix, row, col);
  Print(matrix, row, col);
  return(0);
}

void Print(ARR2D in_array, int rows, int cols) {
  for (int i = 0; i < rows; i++) {
    for (int j = 0; j < cols; j++)
      cout << '\t' << in_array[i][j];
    cout << endl;
  }
}

void Fill(ARR2D in_array, int rows, int cols) {
  for(int i = 0; i < rows; i++)
    for (int j = 0; j < cols; j++)
      in_array[i][j] = 0;

  const int limit = rows * cols;
  int cNum = 1;
  int cRow = 0;
  int cCol = 0;
  int cDir = 0;  // 0-north, 1-east, 2-south, 3-west

  while(true) {
    // Place the number.
    in_array[cRow][cCol] = cNum;
    cNum++;
    if (cNum > limit) break;

    int fRow = cRow;
    int fCol = cCol;
    while (true) {
      fRow = cRow;
      fCol = cCol;
      switch(cDir) {
        case 0: fRow--; break;
        case 1: fCol++; break;
        case 2: fRow++; break;
        case 3: fCol--; break;
      }

      if ( fRow >= 0 && fRow < rows && fCol >= 0 && fCol < cols && in_array[fRow][fCol] == 0)
        break;
      cDir = (cDir + 1) % 4;
    }
    cRow = fRow;
    cCol = fCol;
  }
}

Вопрос 1. Что выводит эта программа, если ввести 3 для строк и 4 для столбцов?

А) 1 2 3
4 5 6
7 8 9
10 11 12
Б) 1 2 3 4
5 6 7 8
9 10 11 12
С) 12 11 10 9
8 7 6 5
4 3 2 1
Д) 1 3 2 4
8 6 7 5
9 11 10 12
Е) 1 2 3 4
10 11 12 5
9 8 7 6
Г) 9 8 7 6
10 11 12 5
1 2 3 4
ЧАС) Ничего не выводит - логика неисправна.
Я) Ничего не выводит - есть синтаксические ошибки.
Дж) Он ничего не выводит - это не положено.
К) Он выводит первые 12 чисел, которые приходят на ум, пока вы ожидаете запуска программы.

Вопрос 2. Что, если мы добавим следующую строку в нашу функцию main()?

MAX_SIZE = 10;
А) Это не разрешено в C++.
Б) Это разрешено; программа будет работать с параметром MAX_SIZE, равным 20
С) Это разрешено; программа будет работать со значением MAX_SIZE, равным 10.

Вопрос 3: Рассмотрим следующие четыре строки из приведенной выше программы:

const int MAX_SIZE = 20;
typedef int ARR2D [MAX_SIZE][MAX_SIZE];

void Print  (ARR2D A, int rows, int cols);
void Fill   (ARR2D A, int rows, int cols);

1) Можно ли использовать константу в typedef?
2) Можно ли использовать typedef в объявлении до того, как переменная этого типа была объявлена?

А) 1) Да 2) Да
Б) 1) Нет 2) Нет
С) 1) Нет 2) Да
Д) 1) Да 2) Нет

Вопрос 4: Можем ли мы использовать следующее:

#define MAX_SIZE 20
вместо:
const int MAX_SIZE = 20;
А) Да, это будет работать, и можно использовать #define для констант в C++.
Б) Да, это будет работать, но мы обычно не используем #define для констант в C++.
С) #define недоступен в C++.
Д) Вы не можете сделать ни одну из этих вещей в C

Вопрос 5: typedef используется для создания псевдонима для имени типа.

А) Истинный.
Б) ЛОЖЬ.

Вопрос 6. Что произойдет, если мы не инициализируем массив значением 0 в функции Fill()?

А) Он будет работать, но на выходе будут все 12.
Б) Он будет работать нормально и генерировать тот же результат, как если бы массив был инициализирован значением 0.
С) Программа не запускается или вылетает
Д) Он будет работать, но на выходе будут все 0.
Е) Он будет работать, но может не генерировать никаких результатов

Вопрос 7: Отметьте все подходящие варианты. Почему в этой программе мы используем const для MAX_SIZE? Не проще ли просто ввести «20» вместо MAX_SIZE там, где это необходимо?

А) MAX_SIZE — это встроенное значение C++, которое может использовать каждый. Просто установите его и используйте.
Б) Глобальных констант следует избегать так же, как и глобальных переменных.
С) Использование константы упрощает понимание нашей программы.
Д) Магические числа в программе обычно считаются хорошей практикой.
Е) Если мы хотим изменить MAX_SIZE, нам нужно изменить его только в одном месте.

Вопрос 8. Оператор переключения в функции Fill() должен иметь регистр по умолчанию, поскольку его включение считается хорошим стилем.

А) Истинный.
Б) ЛОЖЬ.

Вопрос 9: Обратите внимание, что в функции Fill() мы объявляем переменные между операторами. Например, cNum и cRow объявляются и инициализируются после выполнения цикла for. Будет ли это работать на C++ или все переменные придется объявлять в начале функции?

А) Это нормально.
Б) Все переменные должны быть объявлены в верхней части функции.
С) Оба пути неверны: C++ не допускает использования переменных в любом месте программы.
Д) Все переменные должны быть объявлены в глобальной области видимости.

Набор задач 4

Вот набор файлов, определяющих и тестирующих простой класс. Как обычно, отвечайте на последующие вопросы, ссылаясь только на исходный код.

Вот заголовочный файл (cow.h):

#ifndef COW_H
#define COW_H

using namespace std;

typedef enum Color {black, brown, beige, blackandwhite, nocolor};

class Cow {
 public:
  Cow();
  ~Cow();

  // accessors
  double weight() { return weight_; };
  string name() { return name_; };
  Color color() { return color_; };

  // mutators
  void set_name(string inName) { name_ = inName; };
  void set_color(Color inColor) { color_ = inColor; };
  void set_weight(double inWeight) {weight_ = inWeight; };

  void Moo();
  void Properties();

 private:
  Color color_;
  double weight_;
  string name_;
};

#endif

Вот связанный файл .cc (cow.cc):

#include <iostream>
#include "cow.h"

using namespace std;

Cow::Cow() {}

Cow::~Cow() {}

void Cow::Moo() {
  cout << name() << " says MOO." << endl;
}

void Cow::Properties() {
  cout << name() << " weighs " << weight() << ", is "
       << color() << " and says MOO." << endl;
}

А вот клиентская программа для этого класса (cowmain.cc):

#include <iostream>
#include "cow.h"

using namespace std;

int main() {
  Cow cow1;
  cow1.set_name("betsy");
  cow1.set_weight(400.0);
  cow1.set_color(black);

  cow1.Moo();
  cow1.Properties();
}

Вопрос 1: Что выводит эта программа?

А) Бетси говорит МУ.
Бетси весит 400, равна 0 и говорит МУ.
Б) Бетси говорит МУ.
Бетси весит 400 фунтов, она черная и говорит «МУ».
С) Бетси говорит МУ.
Бетси весит 400 фунтов

Вопрос 2. Никогда не следует размещать код методов доступа и мутаторов в заголовочном файле. (Обратите внимание, что аксессор — это метод, который возвращает значение, а мутатор — это метод, который изменяет значение.)

А) Истинный.
Б) ЛОЖЬ.

Вопрос 3. Нужен ли нам «Cow::» перед каждым определением функции в файле «cow.cc»?

А) Нет, поскольку файл коровы включен.
Б) Да

Вопрос 4: Какую роль выполняют:

#ifndef COW_H
#define COW_H
...
#endif

играть в заголовочном файле?

Выберите все, что подходит:

А) Они бесполезны, поскольку имя файла — корова.h, а не COW_H.
Б) Если бы мы этого не сделали, мы бы получили ошибку времени выполнения.
С) Если бы мы этого не сделали, мы могли бы включить файл более одного раза.
Д) Они ничего не делают, потому что одно или несколько ключевых слов написаны с ошибкой.
Е) Они ничего не делают, поскольку класс Cow имеет только один заголовочный файл.

Вопрос 5. Что произойдет, если мы добавим следующую строку в файлowmain.cc?

cow1.weight_ = 24;
А) Программа запустится, и эта строка изменит весовую переменную.
Б) Программа скомпилировалась и запустилась, но на этой строке произошел сбой.
С) С++ этого не позволяет.
Д) Программа скомпилируется и запустится, но переменная веса не изменится в этой строке.

Вопрос 6: При выполнении следующей строки вызывается конструктор класса Cow:

Cow cow1;

Каковы некоторые важные характеристики конструкторов?

Выберите все, что подходит

А) Обычно они не возвращают никаких значений
Б) Если мы не предоставим конструктор в нашем классе, класс не скомпилируется.
С) Конструктор класса Cow нетипичен, поскольку он не инициализирует частные переменные.
Д) Они всегда имеют то же имя, что и класс.
Е) В классе может быть несколько конструкторов, если аргументы различаются.
Ф) Конструктор вызывается при создании экземпляра класса.

Вопрос 7. Каковы некоторые важные характеристики деструктора?

А) Деструктор вызывается, когда объект выходит за пределы области видимости.
Б) Деструктор имеет то же имя, что и класс, но ему предшествует «~».
С) Что-то не так с деструктором в файле корова.cc: он ничего не делает.
Д) Если мы не создадим деструктор для нашего класса, класс не скомпилируется.

Вопрос 8. Учитывая то, как клиентская программа использует класс, учтите следующее:

Разделение членов на публичные и частные в классе Cow нецелесообразно. То есть то, что является частным, должно быть публичным, а то, что является публичным, должно быть частным.

А) Истинный.
Б) ЛОЖЬ.

Вопрос 9: Что, если мы добавим еще один конструктор в дополнение к тому, который у нас есть в коровьем.cc. Новый конструктор выглядит так

Cow::Cow(string inName, double inWeight, Color inColor) {
  set_name(inName);
  set_weight(inWeight);
  set_color(inColor);
}

И мы добавляем следующие строки в main():

Cow cow2("milly", 350.2, brown);
cow2.Moo();
cow2.Properties();

Можем ли мы это сделать?

Выберите все, что подходит

А) Строка в main(), где мы инициализируем корову2, выйдет из строя.
Б) У нас может быть только один конструктор.
С) Это обычное явление в C++
Д) Да, но это не типичное использование C++.
Е) Это будет работать нормально, но ничего не выведет, потому что приваты не инициализированы.
Ф) Мы не можем вызвать setName(), setColor() и setWeight() из метода того же класса.


Бонусные вопросы

Вопрос 1) Каков результат следующего?

#include <iostream>
using namespace std;

void HelpMe(int *p, int *num, int *q);
void WhereAmI(int *p, int *q, int a);

void HelpMe(int *p, int *num, int *q) {
  int a;

  a = 2;
  q = &a;
  *p = *q + *num;
  num = p;
}


void WhereAmI(int *p, int *q, int a) {
  a = 6;
  *p = a + *p;
  *q = a + 3;
  HelpMe(q, &a, p);
}


int main() {
  int *p;
  int q;
  int *num;
  int a;

  a = 3;
  q = 5;
  p = &a;
  num = &q;

  HelpMe(&a, p, num);
  WhereAmI(&q, p, *num);

  cout << "*p = " << *p << " q = " << q << " *num = " << *num << endl;
}
 

Вопрос 2) Рассмотрим следующее утверждение, предполагая, что класс Apple существует и инициализирован. Класс Apple имеет переменную экземпляра color_:

Apple* granny_smith = new Apple; 

Выберите все утверждения ниже, которые верны:

А) Apple* granny_smith = NULL; if (granny_smith == NULL)... Это НЕ нормально: NULL не является значением, которое можно проверить таким способом.
Б) Apple* granny_smith, Фудзи; Это объявляет два указателя на объекты Apple.
С) Переменная granny_smith содержит значения переменных экземпляра, связанные с объектом Apple.
Д) Apple* granny_smith = NULL; Это нормально,
Е) Переменная granny_smith содержит адрес объекта Apple.
Ф) строка gs_color = *(granny_smith.get_color()); Этот оператор возвращает цвет объекта granny_smith, предполагая, что он был инициализирован.
Г) Память для нового объекта Apple выделяется в куче.
ЧАС) Память для нового объекта Apple выделяется в стеке времени выполнения.
Я) интервал* а = &b; Это помещает адрес b в адрес a.


Вопрос 3) Каков результат выполнения следующей программы?

#include <iostream>
using namespace std;

const int kNumVeggies = 4;

void Grill(int squash, int *mushroom);
int Saute(int onions[], int celery);


void Grill(int squash, int *mushroom) {
  *mushroom = squash/4;
  cout << *mushroom + squash << endl;
}

int Saute(int onions[], int celery) {
  celery *= 2;
  onions[celery]++;
  Grill(onions[0], &onions[3]);
  cout << celery << " " << onions[3] << endl;
  return celery;
}

int main() {
  int broccoli, peppers[kNumVeggies], *zucchini;

  for (broccoli = 0; broccoli < kNumVeggies; broccoli++)
    peppers[broccoli] = kNumVeggies - broccoli;
  zucchini = &peppers[Saute(peppers,1)];
  Grill(*zucchini, zucchini);
  zucchini--;
  cout << peppers[3] + *zucchini + *(zucchini + 1) << endl;
}


Ответы на викторину

Вам следует попытаться ответить на все приведенные выше вопросы, не заглядывая в ответы. Лучше попросить кого-нибудь о помощи, чем сразу же обращаться за помощью к листу ответов.

Посмотреть ответы на вышеперечисленные задачи можно здесь .