C++ C++;空和数组索引
是否可以执行以下操作:C++ C++;空和数组索引,c++,C++,是否可以执行以下操作: string word = "Hello"; word[3] = null; if(word[3] == null){/.../} 在C++中,基本上使数组元素为空。例如,如果我想从数组中删除重复的字符,我会先将它们设置为null,然后在每次找到包含null的数组索引时将数组向左移动 如果这是不可能的,在C++中做这样的事情的好方法是什么? 如果要删除相邻的重复字符,可以这样做: std::string::iterator new_end = std::unique(w
string word = "Hello";
word[3] = null;
if(word[3] == null){/.../}
<>在C++中,基本上使数组元素为空。例如,如果我想从数组中删除重复的字符,我会先将它们设置为null,然后在每次找到包含null的数组索引时将数组向左移动
如果这是不可能的,在C++中做这样的事情的好方法是什么?
如果要删除相邻的重复字符,可以这样做:std::string::iterator new_end = std::unique(word.begin(), word.end());
word.erase(new_end, word.end());
如果要标记要删除的任意字符,可以跳过标记,只需为std::remove\u提供适当的谓词,如果:
new_end = std::remove_if(word.begin(), word.end(), IsDuplicate);
word.erase(new_end, word.end());
然而,我想不出一个合适的谓词在这里使用,它不会表现出未定义的行为。我只需编写自己的算法:
template<typename IteratorT>
IteratorT RemoveDuplicates(IteratorT first, IteratorT last)
{
typedef typename std::iterator_traits<IteratorT>::value_type
ValueT;
std::map<ValueT, int> counts;
for (auto scan=first; scan!=last; ++scan)
{
++counts[*scan];
if(counts[*scan] == 1)
{
*first = std::move(*scan);
++first;
}
}
return first;
}
模板
IteratorT RemovedUpplicates(首先是IteratorT,最后是IteratorT)
{
typedef typename std::迭代器特征::值类型
瓦利特;
地图计数;
用于(自动扫描=第一次;扫描!=最后一次;++扫描)
{
++计数[*扫描];
如果(计数[*扫描]==1)
{
*第一个=标准::移动(*扫描);
++第一,;
}
}
先返回;
}
或者,如果您不关心元素的顺序,可以简单地对其排序,然后使用第一种解决方案。如果要删除相邻的重复字符,可以执行以下操作:
std::string::iterator new_end = std::unique(word.begin(), word.end());
word.erase(new_end, word.end());
如果要标记要删除的任意字符,可以跳过标记,只需为std::remove\u提供适当的谓词,如果:
new_end = std::remove_if(word.begin(), word.end(), IsDuplicate);
word.erase(new_end, word.end());
然而,我想不出一个合适的谓词在这里使用,它不会表现出未定义的行为。我只需编写自己的算法:
template<typename IteratorT>
IteratorT RemoveDuplicates(IteratorT first, IteratorT last)
{
typedef typename std::iterator_traits<IteratorT>::value_type
ValueT;
std::map<ValueT, int> counts;
for (auto scan=first; scan!=last; ++scan)
{
++counts[*scan];
if(counts[*scan] == 1)
{
*first = std::move(*scan);
++first;
}
}
return first;
}
模板
IteratorT RemovedUpplicates(首先是IteratorT,最后是IteratorT)
{
typedef typename std::迭代器特征::值类型
瓦利特;
地图计数;
用于(自动扫描=第一次;扫描!=最后一次;++扫描)
{
++计数[*扫描];
如果(计数[*扫描]==1)
{
*第一个=标准::移动(*扫描);
++第一,;
}
}
先返回;
}
或者,如果您不关心元素的顺序,您可以简单地对其排序,然后使用第一种解决方案。我认为您应该看看STL中的算法。
您对要删除的内容不是很明确,但这可能会有所帮助:
std::string string_with_dup("AABBCCDD");
std::string string_without_dup;
std::cout << string_with_dup << std::endl;
// with copy
std::unique_copy(string_with_dup.begin(), string_with_dup.end(), std::back_inserter(string_without_dup));
std::cout << string_without_dup << std::endl;
// or inplace
string_with_dup.erase(std::unique(string_with_dup.begin(), string_with_dup.end()), string_with_dup.end());
std::cout << string_with_dup << std::endl;
std::string string_与_dup(“AABBCCDD”);
std::不带重复的字符串;
std::cout我想你应该看看STL中的算法。
您对要删除的内容不是很明确,但这可能会有所帮助:
std::string string_with_dup("AABBCCDD");
std::string string_without_dup;
std::cout << string_with_dup << std::endl;
// with copy
std::unique_copy(string_with_dup.begin(), string_with_dup.end(), std::back_inserter(string_without_dup));
std::cout << string_without_dup << std::endl;
// or inplace
string_with_dup.erase(std::unique(string_with_dup.begin(), string_with_dup.end()), string_with_dup.end());
std::cout << string_with_dup << std::endl;
std::string string_与_dup(“AABBCCDD”);
std::不带重复的字符串;
std::cout这是可能的,因为字符串的单个元素是char数组中的元素,因此可以表示为指针,即。E您可以检索元素的地址。因此,您可以设置word[3]=null
。如果构造有效,但编译器会打印警告,这是因为NULL
只是一个指针常量。备选方案是:if(!word[3])
或if(word[3]==0)
<>但是无论如何,你应该考虑使用STL来删除重复。 这是可能的,因为字符串的单个元素是字符数组中的元素,因此可以表示为指针I。E您可以检索元素的地址。因此,您可以设置
word[3]=null
。如果构造有效,但编译器会打印警告,这是因为NULL
只是一个指针常量。备选方案是:if(!word[3])
或if(word[3]==0)
<>但是无论如何,你应该考虑使用STL来删除重复。 < P>如果你想删除所有的副本(不只是相邻的副本),你应该使用类似这样的东西
#include <iostream>
#include <map>
#include <string>
#include <algorithm>
using namespace std;
struct is_repeated {
is_repeated( map<char,int>& x ) :r(&x) {};
map<char,int>* r;
bool operator()( char c ) {
(*r)[c]++;
if( (*r)[c] > 1 )
return true;
return false;
}
};
int main (int argc, char**argv)
{
map<char,int> counter_map;
string v = "hello hello hello hello hello hello hello";
cout << v << endl;
is_repeated counter(counter_map);
v.erase( remove_if(v.begin(), v.end(), counter ), v.end() );
cout << v << endl;
}
如果要删除所有重复项(而不仅仅是相邻的重复项),则应将
#include <iostream>
#include <map>
#include <string>
#include <algorithm>
using namespace std;
struct is_repeated {
is_repeated( map<char,int>& x ) :r(&x) {};
map<char,int>* r;
bool operator()( char c ) {
(*r)[c]++;
if( (*r)[c] > 1 )
return true;
return false;
}
};
int main (int argc, char**argv)
{
map<char,int> counter_map;
string v = "hello hello hello hello hello hello hello";
cout << v << endl;
is_repeated counter(counter_map);
v.erase( remove_if(v.begin(), v.end(), counter ), v.end() );
cout << v << endl;
}
相邻的重复字符?或者任何重复的字符?很抱歉,不够具体,但我仅使用字符串作为示例。我想知道如何对包含int或其他常规对象的数组执行某些操作。我对任何重复的字符都感兴趣。相邻的重复字符?或者任何重复的字符?很抱歉,没有非常具体,但我只使用字符串作为示例。我想知道如何对包含int或其他一般对象的数组执行某些操作。我对任何重复项都感兴趣。这似乎是一个非常优雅的方法。你能解释一下它的作用吗?@user1066113:第一个调用unique
函数字符串的范围。它删除所有相邻的重复项,将非重复项向前移动。在移动发生后,它将返回一个迭代器到范围的末尾。然后,此迭代器与字符串成员函数erase
一起使用,以擦除从该点开始到字符串末尾的元素,有效地重新调整大小@user1066113:第二个函数使用remove\u if
函数执行非常类似的操作。但是,它可以根据第三个参数提供的任何条件删除元素,而不是相邻的重复项。我刚刚编写了IsDuplicate
函数。这似乎是一个非常优雅的方法。你能理解吗ou解释它的作用?@user1066113:第一个函数调用字符串整个范围内的unique
函数。该函数删除所有相邻的重复项,将非重复项向前移动。在移动发生后,它将返回一个迭代器到范围的末尾。然后该迭代器与字符串成员函数一起使用de>erase
删除从该点开始到字符串末尾的元素,有效地调整其大小。@user1066113:第二个使用remove\u if
函数执行非常类似的操作。而不仅仅是相邻的重复项