Разочаровывающая ошибка компилятора C ++ относительно неопределенных ссылок - PullRequest
0 голосов
/ 15 февраля 2009

Итак, эта проблема - глупая ошибка, но я уже около часа взламывал ее и, похоже, не могу ее решить.

У меня есть класс main.cpp, который полон случайного дерьма с графическим интерфейсом пользователя (я считаю, что он не совсем соответствует моей проблеме), но в одном из моих методов я делаю ссылку на другой из моих классов "TiffSpec"

TiffSpec - класс, который я написал, и пока в нем нет ошибок компиляции. Я получаю ошибку компиляции:

"неопределенная ссылка на TiffSpec::TiffSpec(std::basic_string<char, std::char_traits<char>, std::allocator<char> >)"

Примечание: я не считаю, что это проблема с классом string, так как я пытался написать конструктор по умолчанию и ссылаться на него, но все равно получил ту же ошибку без "std :: basic _...".

TiffSpec.h, TiffSpec.cpp и main.cpp находятся в одном каталоге.

Вот код в main.cpp вплоть до ошибки:

#include <GL/glut.h>
#include <stdlib.h>
#include <stdio.h>
#include <string>
#include <string.h>
#include <iostream>
#include <sstream>
#include <fstream>
#include <ctype.h>
#include <vector>
#include <list>
#include <typeinfo>
#include <math.h>
#include "TiffSpec.h"



/*  Create checkerboard image   */
#define checkImageWidth 1024

#define checkImageHeight 1024
GLubyte checkImage[checkImageHeight][checkImageWidth][3];

static GLint height;

//list of all non-main methods
void init(void);
void display(void);
void reshape(int w, int h);
void motion(int x, int y);
void read_next_command(unsigned char key, int x, int y);
void makeCheckImage(void);

void main_loop(char line[]);
void evaluateLine(char line[], std::vector<char> delimiters);
void evaluateCommand(std::list<std::string> command);

void read(std::list<std::string> command);
void draw(std::list<std::string> command);
void color(std::list<std::string> command);
void move(std::list<std::string> command);
void TiffStat(std::string fileName);

std::string convertInputToFloating(std::string input);
std::string trimExtraZeros(std::string input);
std::vector<char> getDelimiters();
//end of list


void
TiffStat(std::string fileName)
{
    TiffSpec * testing = new TiffSpec(fileName);
}

Вот начало кода в TiffSpec.h:

#include <GL/glut.h>
#include <stdlib.h>
#include <stdio.h>
#include <string>
#include <string.h>
#include <iostream>
#include <sstream>
#include <fstream>
#include <ctype.h>
#include <vector>
#include <list>
#include <typeinfo>
#include <math.h>
#include <exception>


#ifndef TIFFSPEC_H_
#define TIFFSPEC_H_

using namespace std;


class TiffSpec {
public:
   TiffSpec();
   TiffSpec(std::string filename);

И для хорошей меры, вот код из TiffSpec.cpp

#include "TiffSpec.h"
#include <algorithm>



bool isLittleEndian();
void ByteSwap_(unsigned char * b, int n);
bool tagRecognized(unsigned short tag);
bool fieldTypeRecognized(unsigned short fieldType);
void gatherValues(IFDEntry & entry, ifstream &fileStream);
valueTypes retrieveCorrectType(unsigned short fieldType, unsigned long numberOfValues);
int getFieldByteSize(short fieldType);

TiffSpec::TiffSpec()
{}

TiffSpec::TiffSpec(std::string fileName)
{
std::ifstream fileStream;

Есть идеи, в чем может быть моя проблема? Кроме того, есть ли более эффективный способ обозначить блок кодирования вместо записи 4 пробелов перед каждой строкой? Заглянул в справочник и ничего не увидел ...

Хорошо, я думаю, у меня есть представление о том, что происходит не так. Я впервые использую Eclipse (по крайней мере, в C ++), и MSVS меня побалует. Одним из таких способов является создание файла. Я думаю, что проблема в моем make-файле.

Makefile был предоставлен мне. Я думаю, что мне нужно сделать ссылку на эти новые классы, но где? И нужно ли это делать для файлов .h и .cpp?

Makefile:

SHELL = /bin/sh
prefix = /usr
CC = gcc
C++ = g++ 
GLUT_LIBS = $(prefix)/lib/libglut.so.3
X_LIBADD =  -lXmu -lXext -lXi -lX11
INCLUDES = -Iinclude -I$(prefix)/include  
LDADD = $(GLUT_LIBS) $(prefix)/lib/libGLU.so.1 $(prefix)/lib/libGL.so.1  -lm 
CFLAGS = -g -O2 -Wall -fomit-frame-pointer -ffast-math -fexpensive-optimizations-D_REENTRANT
COMPILE = $(CC) $(DEFS) $(INCLUDES) $(CPPFLAGS) $(CFLAGS)
LINK = $(CC) $(CFLAGS) $(LDFLAGS) -o $@

.SUFFIXES:
.SUFFIXES: .cpp .c .o 

.c.o:
   $(COMPILE) -c $<

.cpp.o:
    $(C++) $(DEFS) $(INCLUDES) $(CPPFLAGS) $(CFLAGS) -c $<

all: main

CLI_OBJECTS=main.o 

main: $(CLI_OBJECTS)
   $(LINK) $(CLI_OBJECTS) $(LDADD) $(LIBS)

clean:
     -rm -f *.o $(PROGRAMS)

Я считаю, что это как-то связано только с присутствием main.o. Но что именно мне нужно написать, чтобы исправить это, мне неизвестно.

Ответы [ 3 ]

4 голосов
/ 15 февраля 2009

Убедитесь, что вы связываете TiffSpec.cpp в свой проект. Как это сделать, зависит от вашей среды разработки.

Для GCC, убедитесь, что вы добавили TiffSpec.o к вашему компоновщику (и, конечно, TiffSpec.cpp в TiffSpec.o).

Для MSVC, убедитесь, что вы добавили TiffSpec.cpp для компиляции и связывания с исполняемым файлом. (FIXME)

2 голосов
/ 15 февраля 2009

Это строка CLI_OBJECTS, которая, кажется, содержит список объектных файлов. Добавить TiffSpec.o:

CLI_OBJECTS=main.o TiffSpec.o

Команда связывания приходит из этого правила в make-файле:

main: $(CLI_OBJECTS)
   $(LINK) $(CLI_OBJECTS) $(LDADD) $(LIBS)

Это говорит о том, что main должен быть построен из файлов, перечисленных в CLI_OBJECTS, выполнив команду в строке ниже.

1 голос
/ 15 февраля 2009

Убедитесь, что вы ссылаетесь в TiffSpec.o.

...