如何在现代C++中使用指针遍历并修改集合?
现代C++中指针遍历修改集合的问题与解决
问题背景
用裸指针遍历并修改C风格数组是可行的,示例代码如下:
char list[3]{'a', 'b', 'c'}; char *pointer{list}; pointer++; *pointer = 'd'; std::cout << list[0] << std::endl; std::cout << list[1] << std::endl; std::cout << list[2] << std::endl;
运行结果:
a d c
但现代C++不推荐裸指针和C风格数组,尝试用std::unique_ptr实现时却未成功:
char list[3]{'a', 'b', 'c'}; std::unique_ptr<char> pointer{std::make_unique<char>(list[0])}; (*pointer)++; *pointer = 'd';
运行后原数组依然是a、b、c,未被修改。
错误原因
你忽略了std::make_unique<char>(list[0])的本质:它创建了一个全新的char对象,值是list[0]的拷贝,并非指向原数组元素的指针。后续对*pointer的修改只作用于这个新对象,和原数组没有任何关联,所以原数组不会变化。
另外,std::unique_ptr<char>是用来管理单个动态分配对象的,不是用来指向已存在栈数组元素的。如果想用智能指针管理整个数组,应该用std::unique_ptr<char[]>,但要注意:如果原数组是栈上分配的,不能让unique_ptr接管它(因为unique_ptr会在销毁时调用delete[],而栈内存不允许被手动释放)。
用std::vector实现的正确方式
std::vector是现代C++推荐的动态容器,支持安全的遍历和修改,有两种常见方式:
方式1:使用迭代器(推荐)
迭代器是容器的安全"指针",无需担心内存管理问题:
#include <vector> #include <iostream> int main() { std::vector<char> vec{'a', 'b', 'c'}; // 获取指向第一个元素的迭代器 auto it = vec.begin(); // 移动迭代器到第二个元素 ++it; // 修改该位置的元素值 *it = 'd'; // 遍历输出结果 for (char c : vec) { std::cout << c << '\n'; } return 0; }
运行结果:
a d c
方式2:使用底层指针(需谨慎)
如果需要类似裸指针的操作,可以通过vector::data()获取指向内部数组的指针,注意只有在vector不扩容(如不执行push_back、resize等可能重新分配内存的操作)时,该指针才有效:
#include <vector> #include <iostream> int main() { std::vector<char> vec{'a', 'b', 'c'}; // 获取指向第一个元素的指针 char* ptr = vec.data(); // 移动指针到第二个元素 ptr++; // 修改元素值 *ptr = 'd'; for (char c : vec) { std::cout << c << '\n'; } return 0; }
运行结果和方式1一致。
内容的提问来源于stack exchange,提问作者Nullndr
相关产品推荐
相关产品推荐

