Начинающий C ++ - проблема с использованием глобальных констант в заголовочном файле - PullRequest
0 голосов
/ 11 мая 2010

Еще один вопрос проекта Scrabble ... Это простой вопрос.

Кажется, у меня проблемы с распознаванием глобальных констант:

Моя доска объявлений.h: http://pastebin.com/7a5Uyvb8

Возвращено ошибок:

1>C:\Users\Francisco\Documents\FEUP\1A2S\PROG\projecto3\projecto3\Board.h(34): error:     variable "TOTAL_ROWS" is not a type name
1>      vector< vector<Cell> > _matrix(TOTAL_ROWS , vector<Cell>(TOTAL_COLUMNS));
1>
1>main.cpp
1>compilation aborted for .\Game.cpp (code 2)
1>Board.cpp
1>.\Board.h(34): error: variable "TOTAL_ROWS" is not a type name
1>      vector< vector<Cell> > _matrix(TOTAL_ROWS , vector<Cell>(TOTAL_COLUMNS));
1>                                     ^
1>

Почему это происходит? Почему компилятор ожидает типы?

Спасибо за ваше время!

EDIT:

Не обращайте внимания на мое предыдущее редактирование ... Это мой конструктор по умолчанию: Совет :: Совет () { _matrix (TOTAL_ROWS, вектор (TOTAL_COLUMNS)); }

Я получаю следующую ошибку.

1>.\Board.cpp(16): error: call of an object of a class type without appropriate operator() or conversion functions to pointer-to-function type
1>       _matrix(TOTAL_ROWS, vector<Cell>(TOTAL_COLUMNS));
1>       ^

Почему это происходит?


Мне удалось решить все проблемы с моим файлом. Я использовал

Board::Board() :
     _matrix(TOTAL_ROWS, vector<Cell>(TOTAL_COLUMNS))
     {}

вместо этого. Спасибо за вашу помощь!

Ответы [ 5 ]

4 голосов
/ 11 мая 2010

Как написано, вы определяете функцию с именем _matrix, которая возвращает вектор. Поэтому ожидается, что TOTAL_ROWS будет именем типа, поскольку оно анализируется как тип параметра. Я предполагаю, что вы пытаетесь определить переменную с именем _matrix, которая является вектором.

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

Оставляя неважные части:

  Board() : _matrix(TOTAL_ROWS, vector<Cell>(TOTAL_COLUMNS)) { }

private:
  vector< vector<Cell> > _matrix;

Обратите внимание, что это всего лишь пример. Предположительно у вас есть файл реализации с фактическим телом для Board(), и вы должны поместить инициализацию туда, а не прямо в заголовок, иначе вы получите ошибки. Важно то, что вы не должны делать это при первоначальном объявлении _matrix.


Для вашего нового вопроса extern const unsigned int TOTAL_COLUMNS = 15; определяет TOTAL_COLUMNS каждый раз, когда Board.h включается в файл. Постоянные переменные в области именного пространства имеют внутреннюю связь по умолчанию, поэтому, если вы пропустите extern, все будет в порядке.

Как правило, если переменная не постоянна, вы применяете подход, аналогичный подходу для _matrix. Вы отключаете инициализацию в заголовке, а затем внутри файла реализации возвращаете его:

board.h: extern const int TOTAL_COLUMNS;

board.cpp: extern const int TOTAL_COLUMNS = 15;

2 голосов
/ 11 мая 2010

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

extern const unsigned int TOTAL_ROWS = 15;
extern const unsigned int TOTAL_COLUMNS = 15;
class Board
{
public:
        Board() : _matrix(TOTAL_ROWS, vector<Cell>(TOTAL_COLUMNS)) {}
private:
        vector< vector<Cell> > _matrix;
};
1 голос
/ 11 мая 2010

Это мой конструктор по умолчанию:

Board :: Board () {_matrix (TOTAL_ROWS, вектор (TOTAL_COLUMNS)); }

Я получаю следующую ошибку. [....]

Вы не следовали примерам и синтаксису, предоставленным @Dennis Zickefoose, @KillianDS и мной.

Пожалуйста, перечитайте наши ответы и изучите наш код.

1 голос
/ 11 мая 2010

В вашем заголовочном файле я вижу:

private:
    vector< vector<Cell> > _matrix(TOTAL_ROWS , vector<Cell>(TOTAL_COLUMNS));

Кажется, это объявление частной переменной-члена _matrix, и, очевидно, это попытка вызвать конструктор для _matrix одновременно. Вы не можете вызвать конструктор таким образом.

Помните, что ваш заголовочный файл может быть включен в МНОГО программных файлов. В результате заголовки не должны содержать инструкций выполнения (существуют определенные исключения, такие как встроенные методы и шаблоны). Вы никогда не знаете, куда будет включен заголовок, поэтому вы никогда не знаете, где появится код в заголовочном файле.

Полезно написать заголовочные файлы, чтобы их было безопасно включать в любом месте .

Если вы хотите продолжить этот код, я предлагаю: Конструктор Board () должен явно создать переменную-член:

Board::Board() :
    _matrix(TOTAL_ROWS, .....);
    // This will call the matrix constructor ONLY when the Board constructor is called.
{
}

Тогда должен вызываться конструктор Board, но ТОЛЬКО в файле .cpp, а не в файле .h.

0 голосов
/ 11 мая 2010

Вы не можете вызвать конструктор в заголовочном файле (или любой другой код).

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...