C++ 中的错误 LNK2005 和 ifndef 不起作用
Error LNK2005 in C++ and ifndef don't work
我对 Visual Studio 2012 和 2015 有疑问,但似乎 "ifndef" 不起作用。我将 "ifndef" 用于 "NAN",将 "ifndef" 用于 header 文件,据说有这 2 个错误(见图)。当我在其他文件的 header 中添加 link "#include"Outil.h"" 时,我看到相同的错误消息。
我以前总是这样做,而且总是有效。我不明白为什么它现在即使只有两个文件也不起作用。
我也尝试更改第一个函数的名称 "realoc_ungraded" 但它不起作用,我得到了同样的错误。
Message of error
留言:
1) 警告:C4005: 'NAN': math.h
的宏重新定义
2) 错误:LNK2005: "struct tab_dynamo __cdecl realoc_ugraded(struct tab_dynamo,unsigned int)" (?realoc_ugraded@@YA?AUtab_dynamo@@U1@I@Z) 已在 main.obj Project1
3) 错误:LNK1169:找到一个或多个多次定义的符号 Projet
有不同文件的代码:
文件main.cpp
#include"Outil.h"
int main(void) {
return 0;
}
文件Outil.h
#ifndef LIBRARY_OF_TOOLS
#define LIBRARY_OF_TOOLS 0
#define _USE_MATH_DEFINES
//NAN not defined in Visual Studio 2012, so I use the def. of VS 2015
#ifndef NAN
#define NAN ((float)(std::numeric_limits<float>::infinity*0.0F))
#endif
#include<iostream>
#include<string>
using namespace std;
#include<cmath>
#include<stdlib.h>
#include<stdio.h>
#include<assert.h>
#define ERROR_ADRESSE 0xcccccccc //default when not initialised
#define DEFAULT_LENGHT_TAB 1
//-----------------------------------------
typedef double type_data; //the type for calculation
//-----------------------------------------
/*Struct for my array*/
typedef struct {
type_data *tab;
unsigned int length;
}tab_dynamo;
//-----------------------------------------
template<typename T>
bool verify_ptr(const T *ptr) {
return (ptr == NULL || ptr == (T*)(ERROR_ADRESSE));
}
//-----------------------------------------
template<typename T>
void see_tab(const T *tab, const unsigned int taille) {
unsigned int i;
cout << endl << endl;
if (verify_ptr(tab) == false && taille > 0) {
cout << endl;
for (i = 0; i<taille; ++i) {
cout << tab[i] << "\t";
}
}
cout << endl << endl;
}
//-----------------------------------------
template<typename T>
T* realoc_ungraded(const T* original_tab, unsigned int *length, const unsigned int new_length) {
T* new_tab = NULL;
unsigned int precedent_length = 0, i;
/*1) Exception case to directly exit*/
if (new_length == 0) {
return NULL;
}
/*2) Verification of the ptr of the length*/
if (verify_ptr(length)) {
length = (unsigned int*)calloc(1, sizeof(unsigned int));
assert(length);
}
precedent_length = *length;
*length = new_length;
/*4) Creation of the new tab.*/
new_tab = (T*)calloc(*length, sizeof(T));
assert(new_tab);
/*5) To transfert data of the original tab to the new tab*/
if (precedent_length != 0 && verify_ptr(original_tab) == false) {
for (i = 0; i < precedent_length && i < new_length; ++i) {
new_tab[i] = original_tab[i];
}
}
return new_tab;
}
//-----------------------------------------
//Version with the use of the struct "tab_dynamo"
tab_dynamo realoc_ungraded(tab_dynamo original_tab, const unsigned int new_length) {
tab_dynamo tableau = { NULL, 0 };
tableau.tab = realoc_ugraded(original_tab.tab, &original_tab.length, new_length);
tableau.length = new_length;
return tableau;
}
#endif
文件Outil.cpp:
#include"Outil.h"
#ifndef NAN
#define NAN ((float)(std::numeric_limits<float>::infinity*0.0F))
#endif
当预处理器处理这些时,NAN 已定义,因为它尚未定义。
#include<cmath>
然后cmath可能包含math.h,发现NAN是你定义的
您可以尝试更改包含的顺序和您的定义。
#include <cmath>
#ifndef NAN
#define NAN ((float)(std::numeric_limits<float>::infinity*0.0F))
#endif
B.T.W如果你使用gcc编译,你可以使用-E选项来查看预处理器的输出并知道预处理如何展开宏。
我对 Visual Studio 2012 和 2015 有疑问,但似乎 "ifndef" 不起作用。我将 "ifndef" 用于 "NAN",将 "ifndef" 用于 header 文件,据说有这 2 个错误(见图)。当我在其他文件的 header 中添加 link "#include"Outil.h"" 时,我看到相同的错误消息。
我以前总是这样做,而且总是有效。我不明白为什么它现在即使只有两个文件也不起作用。
我也尝试更改第一个函数的名称 "realoc_ungraded" 但它不起作用,我得到了同样的错误。
Message of error
留言:
1) 警告:C4005: 'NAN': math.h
的宏重新定义2) 错误:LNK2005: "struct tab_dynamo __cdecl realoc_ugraded(struct tab_dynamo,unsigned int)" (?realoc_ugraded@@YA?AUtab_dynamo@@U1@I@Z) 已在 main.obj Project1
3) 错误:LNK1169:找到一个或多个多次定义的符号 Projet
有不同文件的代码:
文件main.cpp
#include"Outil.h"
int main(void) {
return 0;
}
文件Outil.h
#ifndef LIBRARY_OF_TOOLS
#define LIBRARY_OF_TOOLS 0
#define _USE_MATH_DEFINES
//NAN not defined in Visual Studio 2012, so I use the def. of VS 2015
#ifndef NAN
#define NAN ((float)(std::numeric_limits<float>::infinity*0.0F))
#endif
#include<iostream>
#include<string>
using namespace std;
#include<cmath>
#include<stdlib.h>
#include<stdio.h>
#include<assert.h>
#define ERROR_ADRESSE 0xcccccccc //default when not initialised
#define DEFAULT_LENGHT_TAB 1
//-----------------------------------------
typedef double type_data; //the type for calculation
//-----------------------------------------
/*Struct for my array*/
typedef struct {
type_data *tab;
unsigned int length;
}tab_dynamo;
//-----------------------------------------
template<typename T>
bool verify_ptr(const T *ptr) {
return (ptr == NULL || ptr == (T*)(ERROR_ADRESSE));
}
//-----------------------------------------
template<typename T>
void see_tab(const T *tab, const unsigned int taille) {
unsigned int i;
cout << endl << endl;
if (verify_ptr(tab) == false && taille > 0) {
cout << endl;
for (i = 0; i<taille; ++i) {
cout << tab[i] << "\t";
}
}
cout << endl << endl;
}
//-----------------------------------------
template<typename T>
T* realoc_ungraded(const T* original_tab, unsigned int *length, const unsigned int new_length) {
T* new_tab = NULL;
unsigned int precedent_length = 0, i;
/*1) Exception case to directly exit*/
if (new_length == 0) {
return NULL;
}
/*2) Verification of the ptr of the length*/
if (verify_ptr(length)) {
length = (unsigned int*)calloc(1, sizeof(unsigned int));
assert(length);
}
precedent_length = *length;
*length = new_length;
/*4) Creation of the new tab.*/
new_tab = (T*)calloc(*length, sizeof(T));
assert(new_tab);
/*5) To transfert data of the original tab to the new tab*/
if (precedent_length != 0 && verify_ptr(original_tab) == false) {
for (i = 0; i < precedent_length && i < new_length; ++i) {
new_tab[i] = original_tab[i];
}
}
return new_tab;
}
//-----------------------------------------
//Version with the use of the struct "tab_dynamo"
tab_dynamo realoc_ungraded(tab_dynamo original_tab, const unsigned int new_length) {
tab_dynamo tableau = { NULL, 0 };
tableau.tab = realoc_ugraded(original_tab.tab, &original_tab.length, new_length);
tableau.length = new_length;
return tableau;
}
#endif
文件Outil.cpp:
#include"Outil.h"
#ifndef NAN
#define NAN ((float)(std::numeric_limits<float>::infinity*0.0F))
#endif
当预处理器处理这些时,NAN 已定义,因为它尚未定义。
#include<cmath>
然后cmath可能包含math.h,发现NAN是你定义的
您可以尝试更改包含的顺序和您的定义。
#include <cmath>
#ifndef NAN
#define NAN ((float)(std::numeric_limits<float>::infinity*0.0F))
#endif
B.T.W如果你使用gcc编译,你可以使用-E选项来查看预处理器的输出并知道预处理如何展开宏。