错误C4996:'std :: _ Copy_impl':使用可能不安全的参数的函数调用 [英] error C4996: 'std::_Copy_impl': Function call with parameters that may be unsafe

查看:2711
本文介绍了错误C4996:'std :: _ Copy_impl':使用可能不安全的参数的函数调用的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我知道这个问题在SO中被问过很多次,但这与其他问题有所不同。



编译器错误:带有可能不安全的参数的函数调用



Visual Studio警告C4996



xutility(2227):warning C4996:'std :: _ Copy_impl'



失败代码段

  DWORD dwNumberOfNames = pExportDirectory-> NumberOfNames; 
LPDWORD dwNames =(LPDWORD)((LPBYTE)hDLL + pExportDirectory-> AddressOfNames);
std :: vector< std :: string>出口;
std :: copy(
dwNames,
dwNames + dwNumberOfNames,
[& export,&hDLL](DWORD dwFuncOffset)
{
std :: string fname = std :: string((PCHAR)((PBYTE)hDLL + dwFuncOffset));
exports.push_back(fname);
}
);

编译器错误


错误1错误C4996:'std :: _ Copy_impl':使用参数
的函数调用可能不安全 - 此调用依赖调用者检查
是否通过值是正确的。要禁用此警告,请使用
-D_SCL_SECURE_NO_WARNINGS。查看关于如何使用Visual C ++的Checked IteratorsC:\Program Files(x86)\ Microsoft Visual Studio
11.0 \VC\include\xutility 2176的文档。


问题



考虑到C4996 ,表示函数已标记为已弃用
问题在哪里?


  1. 是否使用std :: copy,MS认为是不安全的,将被弃用?

  2. 是因为我使用了 std :: copy C数组

  3. 是因为我的方式我使用Lambda表达式?

  4. 如果不推荐使用std :: copy,那么如果我需要可移植的话,可以使用其他方法。

注意



我知道,如何抑制警告,但我很好奇,问题的原因?



此外,同样重要的是我知道,便携式的方式来处理这个问题,而不影响代码质量。


<你不是根据msdn调用 std :: copy http://msdn.microsoft.com/en-us/library/x9f6s1wf.aspx



这个函数签名是这样的:

  template< class InputIterator,OutputIterator& 
OutputIterator copy(
InputIterator _First,
InputIterator _Last,
OutputIterator _DestBeg
);

这里没有函子/ lambda的地方。



您未调用 std :: copy_if http://msdn.microsoft.com/en-us/library/ee384415.aspx

  template< class InputIterator,OutputIterator,class BinaryPredicate> 
OutputIterator copy_if(
InputIterator _First,
InputIterator _Last,
OutputIterator _Dest,
Predicate _Pred
);

由于没有输出迭代器,您的谓词也不返回bool。



看起来你想要 std :: transform http://msdn.microsoft.com/en-us/library/391xya49.aspx

  template< class InputIterator,class OutputIterator,class UnaryFunction> 
OutputIterator transform(
InputIterator _First1,
InputIterator _Last1,
OutputIterator _Result,
UnaryFunction _Func
);

您应该在输出迭代器中返回所需的值。所以它会是这样的:

  std :: transform(
dwNames,
dwNames + dwNumberOfNames,
std :: back_inserter(exports),
[& hDLL](DWORD dwFuncOffset)//这个lambda是WRONG
{
//这行是错误
std :: string fname = std :: string((PCHAR)((PBYTE)hDLL + dwFuncOffset));
return fname;
}
);

我的lambda是错误的。你需要输入数组的ELEMENTS(我不确定类型)作为lambda的参数,并返回你想要插入到 exports 中的向量。



您可能也不知道 back_inserter 。它在< iterator> 头中。请参阅: http://msdn.microsoft.com/en-us/library/12awccbs.aspx和此处: http://www.cplusplus.com/reference/iterator/back_inserter/ p>

这可能不是100%的答案,但是,我想你可以到达你想去的地方。


I know this question was asked numerous times in SO, but this is a variation from the rest.

Compiler Error: Function call with parameters that may be unsafe

Visual Studio Warning C4996

xutility(2227): warning C4996: 'std::_Copy_impl'

Failing Code Snippet

DWORD dwNumberOfNames = pExportDirectory->NumberOfNames;
LPDWORD dwNames = (LPDWORD)((LPBYTE)hDLL +  pExportDirectory->AddressOfNames);
std::vector< std::string > exports;
std::copy(
    dwNames, 
    dwNames + dwNumberOfNames, 
    [&exports, &hDLL](DWORD  dwFuncOffset)
{
    std::string fname = std::string((PCHAR)((PBYTE)hDLL + dwFuncOffset));
    exports.push_back(fname);
}
);

Compiler Error

Error 1 error C4996: 'std::_Copy_impl': Function call with parameters that may be unsafe - this call relies on the caller to check that the passed values are correct. To disable this warning, use -D_SCL_SECURE_NO_WARNINGS. See documentation on how to use Visual C++ 'Checked Iterators' C:\Program Files (x86)\Microsoft Visual Studio 11.0\VC\include\xutility 2176

Question

Considering, C4996, means the function was marked to be deprecated Where is the problem?

  1. Is it the use of std::copy, that MS thinks is unsafe and would be deprecated?
  2. Is it because I have used std::copy with a C Array?
  3. Is it because of the way I am using Lambda expression?
  4. If std::copy is deprecated, what is the alternative, if I need to be portable.

Note

I know, how to suppress the warning, but I am curious to know, the root cause of the problem?

Also, equally important for me to know, the portable way to handle this issue without compromising code quality.

解决方案

You aren't calling std::copy according to msdn: http://msdn.microsoft.com/en-us/library/x9f6s1wf.aspx

That function signature is this:

template<class InputIterator, class OutputIterator> 
   OutputIterator copy( 
      InputIterator _First,  
      InputIterator _Last,  
      OutputIterator _DestBeg 
   );

There's no place for a functor/lambda there.

You're not calling std::copy_if either: http://msdn.microsoft.com/en-us/library/ee384415.aspx

template<class InputIterator, class OutputIterator, class BinaryPredicate>
   OutputIterator copy_if(
      InputIterator _First, 
      InputIterator _Last,
      OutputIterator _Dest,
      Predicate _Pred
    );

As you have no output iterator, nor does your predicate return a bool.

It looks like you want std::transform: http://msdn.microsoft.com/en-us/library/391xya49.aspx

template<class InputIterator, class OutputIterator, class UnaryFunction> 
   OutputIterator transform( 
      InputIterator _First1,  
      InputIterator _Last1,  
      OutputIterator _Result, 
      UnaryFunction _Func 
   ); 

And you should be returning the value you want in the output iterator. So it'll be something like this:

std::transform(
    dwNames, 
    dwNames + dwNumberOfNames,
    std::back_inserter(exports),
    [&hDLL](DWORD  dwFuncOffset) // This lambda is WRONG
{
    // THIS LINE IS WRONG 
    std::string fname = std::string((PCHAR)((PBYTE)hDLL + dwFuncOffset));
    return fname;
}
);

My lambda is wrong. You need the input of the ELEMENTS of your array (I'm not sure of the type) as the argument to the lambda, and return what you want inserted into the exports vector.

You probably also didn't know about back_inserter. It's in the <iterator> header. See here: http://msdn.microsoft.com/en-us/library/12awccbs.aspx and here: http://www.cplusplus.com/reference/iterator/back_inserter/

That may not be 100% of the answer, but with that, I think you can get to where you want to go.

这篇关于错误C4996:'std :: _ Copy_impl':使用可能不安全的参数的函数调用的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆