Я попытался передать std::ispunct
в качестве последнего аргумента remove_copy_if
и обнаружил, что его не удалось скомпилировать. Однако, если я передаю ispunct
(только с удаленным std::
), программа компилируется и запускается, как и ожидалось.
код:
#include<iostream>
#include<map>
#include<cctype>
#include<algorithm>
#include<iterator>
using std::map;
using std::string;
string strip_punct(const string &s) {
string target;
remove_copy_if(s.begin(), s.end(), std::back_inserter(target), std::ispunct);
return target;
}
int main() {
string word = "abc.";
string target = strip_punct(word);
std::cout << "target: " << target << "\n";
return 0;
}
сообщение об ошибке:
$ g++ --std=c++11 -o problem_11_4.out problem_11_4.cpp
problem_11_4.cpp: In function 'std::string strip_punct(const string&)':
problem_11_4.cpp:12:80: error: no matching function for call to 'remove_copy_if(std::__cxx11::basic_string<char>::const_iterator, std::__cxx11::basic_string<char>::const_iterator, std::back_insert_iterator<std::__cxx11::basic_string<char> >, <unresolved overloaded function type>)'
12 | remove_copy_if(s.begin(), s.end(), std::back_inserter(target), std::ispunct);
| ^
In file included from /usr/local/Cellar/gcc/9.2.0_1/include/c++/9.2.0/algorithm:62,
from problem_11_4.cpp:4:
/usr/local/Cellar/gcc/9.2.0_1/include/c++/9.2.0/bits/stl_algo.h:703:5: note: candidate: 'template<class _IIter, class _OIter, class _Predicate> _OIter std::remove_copy_if(_IIter, _IIter, _OIter, _Predicate)'
703 | remove_copy_if(_InputIterator __first, _InputIterator __last,
| ^~~~~~~~~~~~~~
/usr/local/Cellar/gcc/9.2.0_1/include/c++/9.2.0/bits/stl_algo.h:703:5: note: template argument deduction/substitution failed:
problem_11_4.cpp:12:80: note: couldn't deduce template parameter '_Predicate'
12 | remove_copy_if(s.begin(), s.end(), std::back_inserter(target), std::ispunct);
| ^
Я искал на SO и нашел этот вопрос: Почему std :: не нужен при использовании ispunct () в C ++? Это полезно, теперь я знаю, что ispunct
можно использовать без std::
. Тем не менее, я написал другую программу и обнаружил, что ispunct
и std::ispunct
оба работают хорошо, когда используются отдельно (не в качестве аргумента). Я до сих пор не понимаю, почему std::
не допускается, когда ispunct
используется в качестве аргумента.