fopen弃用的警告

Visual Studio 2005 C ++编译器上 ,当我的代码使用fopen和这样的调用时,我得到以下警告。

1>foo.cpp(5) : warning C4996: 'fopen' was declared deprecated 1> c:\program files\microsoft visual studio 8\vc\include\stdio.h(234) : see declaration of 'fopen' 1> Message: 'This function or variable may be unsafe. Consider using fopen_s instead. To disable deprecation, use _CRT_SECURE_NO_DEPRECATE. See online help for details.' 

我如何防止这种情况?

它看起来像微软已经不赞成使用缓冲区来提高代码安全性的大量调用。 但是,他们提供的解决scheme并不便携。 无论如何,如果您对使用安全版本的调用(例如fopen_s )不感兴趣,则需要在包含的头文件之前放置_CRT_SECURE_NO_DEPRECATE的定义。 例如:

 #define _CRT_SECURE_NO_DEPRECATE #include <stdio.h> 

预处理器指令也可以添加到项目设置中,以便在项目下的所有文件上生效。 为此,将_CRT_SECURE_NO_DEPRECATE添加到项目属性 – >configuration属性 – > C / C ++ – >预处理器 – >预处理器定义

那么你可以添加一个:

 #pragma warning (disable : 4996) 

在你使用fopen之前,你有没有考虑过使用fopen_s作为警告的build议? 它返回一个错误代码,允许你检查函数调用的结果。

只是禁用弃用的函数警告的问题是,微软可能会删除在CRT的更高版本中有问题的function,打破你的代码(如下面在评论中所述,这是不会发生在这个实例与fopen因为它的一部分C&C ++ ISO标准)。

这只是微软的厚颜无耻。 “已弃用”意味着标准委员会规定的标准语言/标准库未来版本中可能不提供的语言function。 不pipe,也不应该说,“我们单方面不认为你应该使用它”,不pipe这个build议是多么有根据的。

如果您的代码是针对不同的操作系统(如Mac OS X,Linux),则可以使用以下内容:

 #ifdef _WIN32 #define _CRT_SECURE_NO_DEPRECATE #endif 

考虑使用像glib或apache便携式运行库这样的可移植性库。 这些通常提供安全,便携的替代这样的调用。 这也是一件好事,因为这些不安全的调用在大多数现代环境中都被弃用了。

如果你想在很多平台上使用它,你可以像使用定义一样使用:

 #if defined(_MSC_VER) || defined(WIN32) || defined(_WIN32) || defined(__WIN32__) \ || defined(WIN64) || defined(_WIN64) || defined(__WIN64__) errno_t err = fopen_s(&stream,name, "w"); #endif #if defined(unix) || defined(__unix) || defined(__unix__) \ || defined(linux) || defined(__linux) || defined(__linux__) \ || defined(sun) || defined(__sun) \ || defined(BSD) || defined(__OpenBSD__) || defined(__NetBSD__) \ || defined(__FreeBSD__) || defined __DragonFly__ \ || defined(sgi) || defined(__sgi) \ || defined(__MACOSX__) || defined(__APPLE__) \ || defined(__CYGWIN__) stream = fopen(name, "w"); #endif 

对于那些使用Visual Studio 2017版本的人来说,运行不安全操作所需的预处理器定义似乎已经改变。 改用:

 #define _CRT_SECURE_NO_WARNINGS 

它会编译。

我使用VisualStdio 2008.在这种情况下,我经常设置Preprocessor Definitions

菜单\项目\ [ProjectName]属性… Alt + F7

如果单击此菜单或在项目窗口中按Alt + F7,则可以看到“属性页”窗口。

然后看到窗口左侧的菜单。

configuration属性\ C / C ++ \ Preprocessor

然后将_CRT_SECURE_NO_WARNINGS添加到\预处理器定义

许多微软的安全function,包括fopen_s(),都是C11的一部分,所以现在应该是可移植的。 您应该认识到,安全function在exception行为中有所不同,有时也会在返回值中出现。 此外,您需要注意的是,虽然这些函数是标准化的,但它是标准(附录K)的一个可选部分,至lessglibc(Linux上的默认设置)和FreeBSD的libc不能实现。

不过,我打了几年这个问题。 我在这里发布了一组更大的转换macros。 对于您的直接问题,请将以下代码放在包含文件中,并将其包含在源代码中:

 #pragma once #if !defined(FCN_S_MACROS_H) #define FCN_S_MACROS_H #include <cstdio> #include <string> // Need this for _stricmp using namespace std; // _MSC_VER = 1400 is MSVC 2005. _MSC_VER = 1600 (MSVC 2010) was the current // value when I wrote (some of) these macros. #if (defined(_MSC_VER) && (_MSC_VER >= 1400) ) inline extern FILE* fcnSMacro_fopen_s(char *fname, char *mode) { FILE *fptr; fopen_s(&fptr, fname, mode); return fptr; } #define fopen(fname, mode) fcnSMacro_fopen_s((fname), (mode)) #else #define fopen_s(fp, fmt, mode) *(fp)=fopen( (fmt), (mode)) #endif //_MSC_VER #endif // FCN_S_MACROS_H 

当然,这种方法并没有实现预期的exception行为。

我也遇到了同样的问题。 当我尝试添加opencv库

 #include <opencv\cv.h> 

我没有警告,但一个错误。

 error C4996: 'fopen': This function or variable may be unsafe. Consider using fopen_s instead. To disable deprecation, use _CRT_SECURE_NO_WARNINGS. See online help for details. c:\program files (x86)\opencv\build\include\opencv2\flann\logger.h 

我也使用了前面提到的预处理器指令。 但是这并没有解决问题。

我通过如下方式解决了这个问题:

  • 转到属性 – > C / C ++ – >预编译头 – >在预编译头中select不使用预编译头。