我正在使用c ++和XE8。给出以下代码:
String __fastcall RemoveCharsFromString(String &str, const String &c)
{
for(unsigned int i=0; i<c.Length(); ++i)
{
str.Delete(std::remove(str[0], str.LastChar(), c[i]), str.LastChar());
}
}
收到错误:
使用str.Delete(remove(str[0], str.LastChar(), c[i]), str.LastChar());
会产生
for循环中的无法转换&#39; int&#39; to&#39; const char *&#39;
错误。
使用str.Delete(std::remove(str[0], str.LastChar(), c[i]), str.LastChar());
会产生
for循环中的无法找到匹配&#39;删除(wchar_t,wchar_t *,wchar_t)&#39;
错误。
搜索SO和网络时,我的理解是,当使用双引号时,如果使用单引号编写代码,通常会收到此错误。在这种情况下,我不相信这种情况适用。
String
的返回类型是Embarcadero的UnicodeString
。详情请见:RAD Studio VCL Reference - UnicodeString Class
答案 0 :(得分:3)
在C ++ Builder中,String
引用System::String
,它是XE8中System::UnicodeString
的别名。
您的代码中存在很多错误。
System::String::Delete()
方法需要索引和计数作为输入,但这不是您尝试传递给它的。您希望Delete()
像STL std::wstring::erase()
方法一样工作,而事实并非如此。
您没有考虑到System::String::operator[]
是基于1的。它不是基于0的,就像你的代码假设一样。
System::String::LastChar()
方法返回指向字符串中最后一个UTF-16编码的Unicode字符的指针。它不会返回指向字符串的null终止符的指针,就像您的代码所假设的那样。
您正在调用STL std::remove()
算法,该算法将iterator
s范围作为输入,将指定值的所有副本移至范围的末尾,然后返回新的{{1将“已移除”值移动到范围内的位置(因此它们可以是拥有iterator
s的容器中的erase()
'。您不能按照您尝试的方式混合iterator
和System::String::Delete()
。如果你真的想使用std::remove()
,你需要使用它更像这样:
std::replace()
话虽如此,Embarcadero的RTL有自己的System::Sysutils::StringReplace()
功能,您可以使用而不是String __fastcall RemoveCharsFromString(String &str, const String &c)
{
for(int i = 1; i <= c.Length(); ++i)
{
const Char *start = str.c_str();
const Char* end = start + str.Length();
Char* ptr = std::replace(start, end, c[i]);
str.Delete(1 + std::distance(start, ptr), std::distance(ptr, end));
}
}
:
std::replace()
或者,如果您需要在#include <System.SysUtils.hpp>
String __fastcall RemoveCharsFromString(String &str, const String &c)
{
for(int i = 1; i <= c.Length(); ++i)
{
str = StringReplace(str, c[i], L"", TReplaceFlags() << rfReplaceAll);
}
}
字符串(c
未考虑)中考虑使用UTF-16代理人:
std::remove()