检查容器是否为空,以下哪项最有效? 假设'c'是C ++ Containers库的任何容器部分
1. c.begin()==c.end()
2. c.empty()
3. c.size()==0
如果是2,则文档显示“检查,如果容器没有元素,即begin()== end()”但是不表明是否empty()已实现为begin()== end()。那么,empty()究竟是如何实现的呢?
为什么这是错的?
sizeof(c) == 0
答案 0 :(得分:7)
为什么sizeof(c) == 0
错了?每个对象必须有一个地址,这意味着它必须具有1或更大的大小。这意味着sizeof(anything)
始终大于0
。因为sizeof(c) == 0
永远不会成真。
另请注意,sizeof
是编译时操作。它无法为您提供仅在运行时知道的任何内容的大小。例如
char * foo = new char[20];
std::cout << sizeof(foo);
总是会给你指针的大小(在大多数平台上为4或8),而不是指针所指向的内存大小。
答案 1 :(得分:3)
检查空容器的所有三个选项或多或少都相同。使用empty()
节目(已经在评论中表示)显然是你的意图,作为一个小小的奖励,它甚至是最短的一个(对于像我这样的懒人......)。
如何实施?供应商具体,可能内联。使用选项1并非不可能,但不能保证。
类或多或少是任何适当类型的数据集合。它们的内部结构必须在编译时才知道,因此必须总是修复 *) - 因此,它们的大小(必须是...)。
sizeof(c)将返回此固定大小,即使对于容器,无论您放置多少元素,这都是sizeof(c)
错误的原因(实际上,它永远不会得到0,如上所述由NathanOliver在他的回答中,但即使它可以,它也会一直为0,即使容器不为空)。
举例说明sizeof
:让我们看看一些标准容器(我将省略公共界面,只关注数据成员):
template <typename T>
vector
{
size_t capacity;
size_t size;
T* data;
};
这几乎都是矢量需求。包含的数据存储在堆上某处分配的某个数组中,唯一属于vector class 的部分是指针。 sizeof
这样的向量很可能是32(假设size_t和指针大8字节,就像现代64位硬件一样,所以你得到24个字节的成员和另外8个用于指向vtable的指针,只要这个具有虚拟成员的矢量类) - 不断。
template<typename T>
class list
{
class Node
{
Node* next;
Node* previous;
T data;
};
Node* head;
Node* tail;
};
再次 - 仅内部两个指针,内容在堆上某处的节点内分配。 head
和/或tail
可能是一些虚拟节点,以便在begin()
和end()
中使用,但如果是这样的话,那就是
*)
&#34;永远修复&#34; - 在编译时和编译程序的运行期间;如果为不同的机器编译,则 的大小会有所不同(例如,如果为较旧的32位硬件编译,则上面的向量和列表可能具有16和12的大小)。尺寸甚至可以从一个编辑到另一个编辑。 G。由于改变了编译器标志(例如,改变默认对齐,......)。但是在编译期间和编译后,sizeof
正在修复。