#c #lnk
#c #lnk
Вопрос:
Приветствую.
Я искал решение, но я думаю, что эта проблема зависит от личного кода, отсюда и моя публикация здесь.
Перейду сразу к делу.
В моем основном у меня есть два объекта.
Computer *computer = new Computer();
Player *player = new Player();
В классе computer в заголовке у меня есть следующее:
private:
Strategy *strategy;
int winningPosition;
int twoInRow;
int counter;
int makeTwo;
Затем в Computer.cpp:
Computer::Computer(char token, bool hasTurn)
{
m_token = token;
m_hasTurn = hasTurn;
strategy = new Strategy();
}
int Computer::getMove(const char (amp;board)[9])
{
twoInRow = strategy->checkTwoInRow(board);
counter = strategy->counter(board);
makeTwo = strategy->makeTwo(board);
if(twoInRow != 0)
{
return twoInRow - 1;
} else if(counter != 0) {
return counter - 1;
} else if(makeTwo != 0) {
return makeTwo - 1;
} else {
return 0;
}
}
На данный момент я думаю, что проблема возникает.
Все методы, вызываемые из стратегии класса, требуют знания платы, поэтому:
int checkTwoInRow(const char (amp;board)[9]);
int counter(const char (amp;board)[9]);
int makeTwo(const char (amp;board)[9]);
Проблемы, которые я получаю, отключая их для компиляции:
Error 1 error LNK2019: unresolved external symbol "public: int __thiscall Strategy::makeTwo(char const (amp;)[9])" (?makeTwo@Strategy@@QAEHAAY08$$CBD@Z) referenced in function "public: int __thiscall Computer::getMove(char const (amp;)[9])" (?getMove@Computer@@QAEHAAY08$$CBD@Z) C:CPPTTTComputer.obj tictactoeCPP
Error 2 error LNK2019: unresolved external symbol "public: int __thiscall Strategy::counter(char const (amp;)[9])" (?counter@Strategy@@QAEHAAY08$$CBD@Z) referenced in function "public: int __thiscall Computer::getMove(char const (amp;)[9])" (?getMove@Computer@@QAEHAAY08$$CBD@Z) C:CPPTTTComputer.obj tictactoeCPP
Error 3 error LNK2019: unresolved external symbol "public: int __thiscall Strategy::checkTwoInRow(char const (amp;)[9])" (?checkTwoInRow@Strategy@@QAEHAAY08$$CBD@Z) referenced in function "public: int __thiscall Computer::getMove(char const (amp;)[9])" (?getMove@Computer@@QAEHAAY08$$CBD@Z) C:CPPTTTComputer.obj tictactoeCPP
Как новичок в c , я абсолютно понятия не имею, почему или как вызвана эта проблема. Я думаю, что это должно быть как-то связано либо с созданием экземпляра Strategy в классе computer, либо с параметром, переданным с компьютера стратегии в вызовах метода.
Кто-нибудь может объяснить, ПОЧЕМУ возникает эта ошибка, я вообще не совсем понимаю ошибку. А также как это решить / предотвратить?
Редактировать*
Я только что получил запрос на предоставление общего доступа к классу Strategy:
Strategy.h:
#pragma once
class Strategy
{
public:
Strategy(void);
~Strategy(void);
int checkTwoInRow(const char (amp;board)[9]);
int counter(const char (amp;board)[9]);
int makeTwo(const char (amp;board)[9]);
};
Класс определил эти методы, я не буду их публиковать, потому что они довольно длинные.
Комментарии:
1. Покажите нам класс Strategy, и это класс descendent, я думаю, что именно в этом заключается ваша проблема.
2. @Tony подойдет. Спасибо за уведомление.
3. Также попробовал один раз изменить #pragma на #ifndef STRATEGY_H и #define STRATEGY_H (хотя я пока этого не совсем понимаю, это именно то, что я использую в других заголовках), и это ничего не меняет._.
Ответ №1:
Это ошибка компоновки, и она не имеет ничего общего с созданием экземпляров или параметрами.
Вы не предоставили компоновщику определения для этих функций. Если вы определили их в Strategy.cpp вам нужно скомпилировать это и добавить в качестве аргумента компоновщику. То, как вы это сделаете, полностью зависит от того, какие инструменты вы используете для сборки своей программы.
Если вы используете Visual Studio (или любую другую среду IDE), она должна позаботиться об этом автоматически после добавления Strategy.cpp для вашего проекта.
Или, возможно, вы определили их следующим образом:
int checkTwoInRow(const char (amp;board)[9])
{
// Do something with board the wrong way
}
вместо этого:
int Strategy::checkTwoInRow(const char (amp;board)[9])
{
// Do something with board the right way
}
Первый не определяет функцию-член стратегии, он определяет глобальную функцию.
Комментарии:
1. Я определил их, используя вторую версию: Strategy::checkTwoInRow. Спасибо за ваше объяснение. Проблема более чем ясна 🙂 Спасибо вам. Если вы не возражаете, я хотел бы спросить вас еще об одной вещи. Это то, что делают #ifndef и #define?
2. Хорошо, только что нашел проблему. Я был довольно глуп, я действительно использовал вашу первую версию. Забыл использовать Strategy :: … даже после того, как убедился, что я это сделал, потому что я всегда делаю с файлами классов… но на этот раз я просто забыл. Большое спасибо.
3. @Joey Roosing : Именно это я имел в виду, «случайно определив их как свободные функции». :-]
Ответ №2:
Ошибка просто указывает на то, что вы объявили, но не определили функции-члены Strategy::makeTwo
, Strategy::counter
и Strategy::checkTwoInRow
. Вы уверены, что реализовали их (в исходном файле, который фактически компилируется) и что вы случайно не определили их как свободные функции?
Комментарии:
1. На самом деле, я вообще не определял их в заголовке. нужно определить Strategy::counter в заголовке Computer?
2. @Joey Roosing : Убедитесь, что вы понимаете разницу между объявлением и определением. Вы показали их объявления в своем первоначальном вопросе (предположительно, это был отрывок из
class Strategy
), но где на самом деле реализованы эти функции-члены?3. Они реализованы в классе Strategy, и все три из них возвращают целое число. И да, вы правы. Я перепутал определение и объявление. Извините за это. методы определены и объявлены в классе Strategy, и мне нужно получить к ним доступ в классе computer