aki*_*kif 133 c++ header redefinition
如何防止包含两次头文件?问题是我包括了在MyClass.h中然后我将MyClass.h包含在许多文件中,因此它包含多次并发生重定义错误.怎么预防?
我正在使用#pragma而不是包含警卫,我想这很好.
MyClass.h:
// MyClass.h
#pragma once
#include <winsock2.h>
class MyClass
{
// methods
public:
MyClass(unsigned short port);
virtual ~MyClass(void);
};
Run Code Online (Sandbox Code Playgroud)
编辑:我得到的错误很少
c:\program files\microsoft sdks\windows\v6.0a\include\ws2def.h(91) : warning C4005: 'AF_IPX' : macro redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(460) : see previous definition of 'AF_IPX'
c:\program files\microsoft sdks\windows\v6.0a\include\ws2def.h(124) : warning C4005: 'AF_MAX' : macro redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(479) : see previous definition of 'AF_MAX'
c:\program files\microsoft sdks\windows\v6.0a\include\ws2def.h(163) : warning C4005: 'SO_DONTLINGER' : macro redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(402) : see previous definition of 'SO_DONTLINGER'
c:\program files\microsoft sdks\windows\v6.0a\include\ws2def.h(206) : error C2011: 'sockaddr' : 'struct' type redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(485) : see declaration of 'sockaddr'
c:\program files\microsoft sdks\windows\v6.0a\include\ws2def.h(384) : error C2143: syntax error : missing '}' before 'constant'
c:\program files\microsoft sdks\windows\v6.0a\include\ws2def.h(384) : error C2143: syntax error : missing ';' before 'constant'
c:\program files\microsoft sdks\windows\v6.0a\include\ws2def.h(384) : error C2059: syntax error : 'constant'
c:\program files\microsoft sdks\windows\v6.0a\include\ws2def.h(437) : error C2143: syntax error : missing ';' before '}'
c:\program files\microsoft sdks\windows\v6.0a\include\ws2def.h(437) : error C4430: missing type specifier - int assumed. Note: C++ does not support default-int
c:\program files\microsoft sdks\windows\v6.0a\include\ws2def.h(437) : error C4430: missing type specifier - int assumed. Note: C++ does not support default-int
c:\program files\microsoft sdks\windows\v6.0a\include\ws2def.h(518) : warning C4005: 'IN_CLASSA' : macro redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(287) : see previous definition of 'IN_CLASSA'
c:\program files\microsoft sdks\windows\v6.0a\include\ws2def.h(524) : warning C4005: 'IN_CLASSB' : macro redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(293) : see previous definition of 'IN_CLASSB'
c:\program files\microsoft sdks\windows\v6.0a\include\ws2def.h(530) : warning C4005: 'IN_CLASSC' : macro redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(299) : see previous definition of 'IN_CLASSC'
c:\program files\microsoft sdks\windows\v6.0a\include\ws2def.h(541) : warning C4005: 'INADDR_ANY' : macro redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(304) : see previous definition of 'INADDR_ANY'
c:\program files\microsoft sdks\windows\v6.0a\include\ws2def.h(543) : warning C4005: 'INADDR_BROADCAST' : macro redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(306) : see previous definition of 'INADDR_BROADCAST'
c:\program files\microsoft sdks\windows\v6.0a\include\ws2def.h(577) : error C2011: 'sockaddr_in' : 'struct' type redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(312) : see declaration of 'sockaddr_in'
c:\program files\microsoft sdks\windows\v6.0a\include\winsock2.h(132) : error C2011: 'fd_set' : 'struct' type redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(68) : see declaration of 'fd_set'
c:\program files\microsoft sdks\windows\v6.0a\include\winsock2.h(167) : warning C4005: 'FD_SET' : macro redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(102) : see previous definition of 'FD_SET'
c:\program files\microsoft sdks\windows\v6.0a\include\winsock2.h(176) : error C2011: 'timeval' : 'struct' type redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(111) : see declaration of 'timeval'
c:\program files\microsoft sdks\windows\v6.0a\include\winsock2.h(232) : error C2011: 'hostent' : 'struct' type redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(167) : see declaration of 'hostent'
c:\program files\microsoft sdks\windows\v6.0a\include\winsock2.h(245) : error C2011: 'netent' : 'struct' type redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(180) : see declaration of 'netent'
c:\program files\microsoft sdks\windows\v6.0a\include\winsock2.h(252) : error C2011: 'servent' : 'struct' type redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(187) : see declaration of 'servent'
c:\program files\microsoft sdks\windows\v6.0a\include\winsock2.h(264) : error C2011: 'protoent' : 'struct' type redefinition
c:\program files\microsoft sdks\windows\v6.0a\include\winsock.h(199) : see declaration of 'protoent'
Run Code Online (Sandbox Code Playgroud)
pin*_*33n 219
包含<windows.h>之前包含此问题<winsock2.h>.尝试安排首先<windows.h>包含<winsock2.h>或_WINSOCKAPI_首先定义的包含列表:
#define _WINSOCKAPI_ // stops windows.h including winsock.h
#include <windows.h>
// ...
#include "MyClass.h" // Which includes <winsock2.h>
Run Code Online (Sandbox Code Playgroud)
另请参见本.
Pav*_*iak 73
正如其他人所说,问题在于windows.h之前是否包括在内WinSock2.h.因为windows.h包括winsock.h.你不能同时使用WinSock2.h和winsock.h.
解决方案:
包括WinSock2.h之前windows.h.对于预编译头文件,您应该在那里解决它.在简单项目的情况下,很容易.但是在大型项目中(特别是在编写可移植代码时,没有预编译头文件),这可能非常困难,因为当WinSock2.h包含头文件时,windows.h可能已经包含在其他一些头文件/实现文件中.
定义WIN32_LEAN_AND_MEAN之前windows.h或项目范围.但它会排除你可能需要的许多其他东西,你应该自己包括它.
定义_WINSOCKAPI_之前windows.h或项目范围.但是,当您包含时,您将WinSock2.h获得宏重新定义警告.
使用windows.h而不是WinSock2.h什么时候winsock.h足够你的项目(在大多数情况下是).这可能会导致更长的编译时间,但可以解决任何错误/警告.
Dan*_*ull 15
哦 - Windows的丑陋......包含的顺序在这里很重要.你需要在windows.h之前包含winsock2.h.由于windows.h可能包含在预编译头文件(stdafx.h)中,因此您需要包含winsock2.h:
#include <winsock2.h>
#include <windows.h>
Run Code Online (Sandbox Code Playgroud)
Dev*_*lar 14
通过使用"标题保护":
#ifndef MYCLASS_H
#define MYCLASS_H
// This is unnecessary, see comments.
//#pragma once
// MyClass.h
#include <winsock2.h>
class MyClass
{
// methods
public:
MyClass(unsigned short port);
virtual ~MyClass(void);
};
#endif
Run Code Online (Sandbox Code Playgroud)
我检查递归包括,我看到的头文件,其中包括(递归地)一些#include "windows.h"和#include "Winsock.h"和写#include "Winsock2.h"。在这个文件中,我添加#include "Winsock2.h"为第一个包含。
耐心一点,一一查看include并建立这个顺序,先 #include "Winsock2.h"然后#include "windows.h"
当我试图拉出第三方软件包时,我遇到了这个问题,这个软件包显然包含了某些东西,其中有一些标题._WINSOCKAPI_在项目层面定义比趟过汤和修复有问题的包括更容易(更不用说更易于维护).
小智 5
我找到了此链接windows.h和winsock2.h,它对我来说很有用:
#define _WINSOCKAPI_ // stops windows.h including winsock.h
#include <windows.h>
#include <winsock2.h>
Run Code Online (Sandbox Code Playgroud)
我在查找问题发生的位置时遇到了麻烦,但是通过添加#define,我能够在不弄清楚问题的情况下进行构建。
小智 5
在VS 2015中,以下将起作用:
#define _WINSOCKAPI_
Run Code Online (Sandbox Code Playgroud)
虽然以下内容不会:
#define WIN32_LEAN_AND_MEAN
Run Code Online (Sandbox Code Playgroud)
您应该使用标头保护。
将这些行放在头文件的顶部
#ifndef PATH_FILENAME_H
#define PATH_FILENAME_H
Run Code Online (Sandbox Code Playgroud)
并在底部
#endif
Run Code Online (Sandbox Code Playgroud)