string.erase 函数在特定情况下不起作用
string.erase function is not working in a specific case
我有以下格式的字符串:"name.bag.csv"
我想从字符串中删除“.bag”。
这是我尝试 运行:
的代码示例
csv_file_name = "loololololool.bag.csv";
csv_file_name.erase(csv_file_name.end()-8, 4);
std::cout << csv_file_name << std::endl;
但是我在第二行收到一个错误:
no matching function for call to ‘std::__cxx11::basic_string<char>::erase(__gnu_cxx::__normal_iterator<char*, std::__cxx11::basic_string<char> >, int)’
csv_file_name.erase(csv_file_name.end()-8, 4);
好像只有一个参数。
但是,如果我这样做:
csv_file_name = "loololololool.bag.csv";
csv_file_name.erase(13, 4);
std::cout << csv_file_name << std::endl;
它似乎工作正常。另外当我执行
csv_file_name = "loololololool.bag.csv";
csv_file_name.erase(csv_file_name.end()-8);
std::cout << csv_file_name << std::endl;
它按原样删除了单个字符。
这怎么会发生? csv_file_name.end()-8
必须有效,因为它会删除单个字符。采取两个论点也应该有效。但是组合没有?请帮忙!
您混淆了迭代器和索引。
string.erase(iter) //删除迭代器指向的字符
string.erase(iter1, iter2) // 删除两个迭代器之间的字符
string.erase(index, count) // 删除从 index
开始的 count 个字符
csv_file_name.end()-8
是一个迭代器,erase
没有采用迭代器和索引或计数的版本。
而不是
csv_file_name.erase(csv_file_name.end()-8, 4);
我想你的意思是
csv_file_name.erase(csv_file_name.size()-8, 4);
但实际上您应该能够阅读文档并自己解决这些问题。这样你会更有效率。
您混淆了 std::string::erase 的签名。有适用于一个或两个整数位置的重载,以及适用于一个或两个迭代器的另一组重载,请参阅 here.
您要做的是使用签名(迭代器、整数)调用擦除。这种重载根本不存在。
编辑太晚了:)
#include <bits/stdc++.h>
using namespace std;
/*
I have used this for this demonstration. However, it is
not recommended to write this in larger projects. Please refer this
*/
int main() {
//I have taken the position of the first dot. This is the position
//from where I am deleting 4 characters including the first dot.
//This holds true given the structure of the string is as below.
//Please note that as long as the string follows this structure
//<any number of characters>.bag<any number of characters> this will pass.
string s1 = "loololololool.bag.csv";
string s2 = "loololololool.bag.csv";
cout << "Demo 1 Analysis \n";
//Please consult this link http://www.cplusplus.com/reference/string/string/erase/
//Demo signature #1 string& erase (size_t pos = 0, size_t len = npos);-------
int posFirstDot1 = s1.find('.');
string result1 = s1.erase(posFirstDot1, 4);
cout << s1 << endl;
cout << "Address of result1 : " << &result1 << " and address of s1 : " << &s1 << endl;
//Note that result1 and s1 are same but are present at different addresses. Thats Subtle :)
//----------------------------------
cout << "Demo 2 Analysis\n";
//Demo signature #3 iterator erase (const_iterator first, const_iterator last);
int posFirstDot2 = s2.find('.');
//get an iterator with s.begin() and posFirstDot3
auto itFirstDot2 = next(s2.begin(), posFirstDot2);
//we want to delete the next 4 characters starting from position of first dot
auto itLastCharacterToBeRemoved = next(itFirstDot2, 4);
auto result3 = s2.erase(itFirstDot2, itLastCharacterToBeRemoved);
cout << s2 << endl;
return 0;
}
我有以下格式的字符串:"name.bag.csv" 我想从字符串中删除“.bag”。 这是我尝试 运行:
的代码示例csv_file_name = "loololololool.bag.csv";
csv_file_name.erase(csv_file_name.end()-8, 4);
std::cout << csv_file_name << std::endl;
但是我在第二行收到一个错误:
no matching function for call to ‘std::__cxx11::basic_string<char>::erase(__gnu_cxx::__normal_iterator<char*, std::__cxx11::basic_string<char> >, int)’
csv_file_name.erase(csv_file_name.end()-8, 4);
好像只有一个参数。 但是,如果我这样做:
csv_file_name = "loololololool.bag.csv";
csv_file_name.erase(13, 4);
std::cout << csv_file_name << std::endl;
它似乎工作正常。另外当我执行
csv_file_name = "loololololool.bag.csv";
csv_file_name.erase(csv_file_name.end()-8);
std::cout << csv_file_name << std::endl;
它按原样删除了单个字符。
这怎么会发生? csv_file_name.end()-8
必须有效,因为它会删除单个字符。采取两个论点也应该有效。但是组合没有?请帮忙!
您混淆了迭代器和索引。
string.erase(iter) //删除迭代器指向的字符
string.erase(iter1, iter2) // 删除两个迭代器之间的字符
string.erase(index, count) // 删除从 index
开始的 count 个字符
csv_file_name.end()-8
是一个迭代器,erase
没有采用迭代器和索引或计数的版本。
而不是
csv_file_name.erase(csv_file_name.end()-8, 4);
我想你的意思是
csv_file_name.erase(csv_file_name.size()-8, 4);
但实际上您应该能够阅读文档并自己解决这些问题。这样你会更有效率。
您混淆了 std::string::erase 的签名。有适用于一个或两个整数位置的重载,以及适用于一个或两个迭代器的另一组重载,请参阅 here.
您要做的是使用签名(迭代器、整数)调用擦除。这种重载根本不存在。
编辑太晚了:)
#include <bits/stdc++.h>
using namespace std;
/*
I have used this for this demonstration. However, it is
not recommended to write this in larger projects. Please refer this
*/
int main() {
//I have taken the position of the first dot. This is the position
//from where I am deleting 4 characters including the first dot.
//This holds true given the structure of the string is as below.
//Please note that as long as the string follows this structure
//<any number of characters>.bag<any number of characters> this will pass.
string s1 = "loololololool.bag.csv";
string s2 = "loololololool.bag.csv";
cout << "Demo 1 Analysis \n";
//Please consult this link http://www.cplusplus.com/reference/string/string/erase/
//Demo signature #1 string& erase (size_t pos = 0, size_t len = npos);-------
int posFirstDot1 = s1.find('.');
string result1 = s1.erase(posFirstDot1, 4);
cout << s1 << endl;
cout << "Address of result1 : " << &result1 << " and address of s1 : " << &s1 << endl;
//Note that result1 and s1 are same but are present at different addresses. Thats Subtle :)
//----------------------------------
cout << "Demo 2 Analysis\n";
//Demo signature #3 iterator erase (const_iterator first, const_iterator last);
int posFirstDot2 = s2.find('.');
//get an iterator with s.begin() and posFirstDot3
auto itFirstDot2 = next(s2.begin(), posFirstDot2);
//we want to delete the next 4 characters starting from position of first dot
auto itLastCharacterToBeRemoved = next(itFirstDot2, 4);
auto result3 = s2.erase(itFirstDot2, itLastCharacterToBeRemoved);
cout << s2 << endl;
return 0;
}