简体   繁体   English

char* buffer = new vs char buffer[] in C++

[英]char* buffer = new vs char buffer[] in C++

1. char* buffer = new char[size]
2. char buffer[size]

I'm new to C++ and I see most places creating buffers using the first example.我是 C++ 的新手,我看到大多数地方都使用第一个示例创建缓冲区。 I know in the first method, the data in that part of memory can be passed on until manually deleted using delete[] .我知道在第一种方法中,可以传递该部分内存中的数据,直到使用delete[]手动删除。 While using the second method, the buffer would have a lifetime depending on the scope.使用第二种方法时,缓冲区的生命周期取决于作用域。 If I only plan on the buffer lasting through a particular function and I don't plan on passing it to anything else, does it matter which method I use?如果我只计划通过特定函数持续使用缓冲区,并且不打算将其传递给其他任何东西,那么我使用哪种方法有关系吗?

char* buffer = new char[size]

This is portable, but should be avoided.这是可移植的,但应该避免。 Until you really know what you're doing, using new directly is almost always a mistake (and when you do know what you're doing, it's still a mistake, but you'll know that without being told).在你真正知道你在做什么之前,直接使用new几乎总是一个错误(当你知道你在做什么时,它仍然是一个错误,但你会在不被告知的情况下知道这一点)。

char buffer[size]

This depends on how you've defined size .这取决于您如何定义size If it's a constant (and fairly small), then this is all right.如果它是一个常数(并且相当小),那么这没问题。 If it's not a constant, then any properly functioning compiler is required to reject it (but some common ones accept it anyway).如果它不是常量,那么任何正常运行的编译器都需要拒绝它(但一些常见的编译器无论如何都会接受它)。

If it's constant, but "large", the compiler will accept the code, but it's likely to fail when you try to execute it.如果它是常量,但是“大”,编译器将接受代码,但是当您尝试执行它时它可能会失败。 In this case, anything over a million is normally too large, and anything more than a few hundred thousand or so becomes suspect.在这种情况下,超过一百万的任何东西通常都太大了,而超过几十万左右的任何东西都会变得可疑。

There is one exception to that though: if this is defined outside any function (ie, as a global variable), then it can safely be much larger than a local variable can be.但是有一个例外:如果 this 在任何函数之外定义(即,作为全局变量),那么它可以安全地比局部变量大得多。 At the same time, I feel obliged to point out that I consider global variables something that should normally be avoided as a rule (and I'm far from being alone in holding that opinion).同时,我觉得有必要指出,我认为全局变量是通常应该避免的规则(而且我远非唯一持有这种观点的人)。

Also note that these two are (more or less) mutually exclusive: if size is a constant, you generally want to avoid dynamic allocation, but it has to be a constant to just define an array (again, with a properly functioning compiler).另请注意,这两者(或多或少)是相互排斥的:如果size是一个常量,您通常希望避免动态分配,但它必须是一个常量才能仅定义一个数组(同样,使用正常运行的编译器)。

Unless size is fairly small constant, most of the time you should avoid both of these.除非size是相当小的常数,否则大多数时候你应该避免这两种情况。 What you most likely want is either:您最有可能想要的是:

std::string buffer;

or:或者:

std::vector<char> buffer(size);

or possibly:或者可能:

std::array<char, size> buffer;

The first two of these can allocate space for the buffer dynamically, but generally keep the allocation "hidden", so you don't normally need to deal with it directly.其中前两个可以为缓冲区动态分配空间,但一般保持分配“隐藏”,因此您通常不需要直接处理它。 The std::array is pretty much like the char buffer[size] , (eg, has a fixed size, and is really on suitable for fairly small sizes) but enforces that the size has to be a const, and gives you roughly the same interface as vector (minus anything that would change the number of elements, since that's a constant with std::array ). std::array非常类似于char buffer[size] ,(例如,具有固定大小,并且确实适用于相当小的大小)但强制大小必须是一个常量,并大致为您提供与vector相同的接口(减去任何会改变元素数量的东西,因为这是std::array的常量)。

Main difference is that the first variant is dynamic allocation and the second one is not.主要区别在于第一个变体是动态分配,而第二个不是。 You require dynamic allocation when you do not know at compile time, how much memory you will need.当您在编译时不知道需要多少内存时,您需要动态分配。 That means when "size" is not entirely a constant but somehow calculated at runtime depending on external input.这意味着当“大小”不完全是一个常数,而是在运行时根据外部输入以某种方式计算时。

It is a good practice¹ to use containers that handle dynamic memory internally and thus ensure that you do not have to delete manually which is often a source for bugs and memory leaks.使用在内部处理动态内存的容器是一个很好的做法¹,从而确保您不必手动删除,这通常是错误和内存泄漏的根源。 A common, dynamic container for all kinds of data is std::vector<char> (don't forget to #include <vector> )用于各种数据的通用动态容器是std::vector<char> (不要忘记#include <vector>

However if you do handle texts, use the class std::string which also handles the memory internally.但是,如果您确实处理文本,请使用std::string类,它也在内部处理内存。 Raw char* arrays are a remainder from old C.原始char*数组是旧 C 的余数。

¹that good practice has the main exception when you don't use primitive data types but your own classes which store some massive amount of data. ¹当您不使用原始数据类型而是使用您自己的存储大量数据的类时,良好的做法有一个主要的例外。 Reason is that std::vector<> performs copy operations when resized (and those are more expensive the larger the data).原因是std::vector<>在调整大小时执行复制操作(并且数据越大,这些操作就越昂贵)。 However once you have come that far in your C++ projects, you should know about "smart pointers" by then which are the safe solution for those special cases.然而,一旦你在你的 C++ 项目中走得那么远,你应该知道“智能指针”是那些特殊情况的安全解决方案。

By the way, with &the_vector[0] (address of the first element in the vector) you can get a pointer that behaves pretty much like the char array and thus can be used for older functions that do not accept vectors directly.顺便说一下,使用&the_vector[0] (向量中第一个元素的地址),您可以获得一个指针,其行为与 char 数组非常相似,因此可用于不直接接受向量的旧函数。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM