最近我发现了很多例子,其中大多数都是关于C ++ 98的,反正我已经创建了我的简单数组和循环(codepad):
#include <iostream>
using namespace std;
int main ()
{
string texts[] = {"Apple", "Banana", "Orange"};
for( unsigned int a = 0; a < sizeof(texts); a = a + 1 )
{
cout << "value of a: " << texts[a] << endl;
}
return 0;
}
输出:
value of a: Apple value of a: Banana value of a: Orange Segmentation fault
除了最后的分段错误外,它工作正常。
我的问题是,这个数组/循环是否是一个好方法?我正在使用C ++ 11,所以我想确保它符合标准并且无法以更好的方式完成?
答案 0 :(得分:71)
在C / C ++中sizeof
。始终给出整个对象中的字节数,并将数组视为一个对象。注意:sizeof
一个指针 - 指向数组的第一个元素或单个对象 - 给出指针的大小,而不是指向的对象。无论哪种方式,sizeof
不都会给出数组中元素的数量(长度)。要获得长度,您需要除以每个元素的大小。例如,
for( unsigned int a = 0; a < sizeof(texts)/sizeof(texts[0]); a = a + 1 )
至于使用C ++ 11方式,最好的方法可能是
for(const string &text : texts)
cout << "value of text: " << text << endl;
这让编译器可以计算出你需要多少次迭代。
编辑:正如其他人所指出的那样,{+ 1}}在C ++ 11中优于原始数组;但是,没有其他答案解决了为什么std::array
失败的原因,所以我仍然认为这是更好的答案。
答案 1 :(得分:16)
string texts[] = {"Apple", "Banana", "Orange"};
for( unsigned int a = 0; a < sizeof(texts); a = a + 1 )
{
cout << "value of a: " << texts[a] << endl;
}
不。完全是一种迭代数组的错误方法。 sizeof(texts)
不等于数组中元素的数量!
现代的C ++ 11方式是:
std::array
;或std::vector
的大小取决于运行时间,则使用#include <iostream>
#include <array>
int main() {
std::array<std::string, 3> texts = {"Apple", "Banana", "Orange"};
// ^ An array of 3 elements with the type std::string
for(const auto& text : texts) { // Range-for!
std::cout << text << std::endl;
}
}
然后在迭代时使用range-for。
std::array
您可能会问,std::vector
如何比ol'C数组更好?答案是它具有其他标准库容器的额外安全性和功能,大多与std::begin/end
非常相似。此外,答案是它不具有衰减到指针的怪癖,从而丢失类型信息,一旦丢失原始数组类型,就不能在其上使用range-for或{{1}}。
答案 2 :(得分:8)
sizeof
告诉你事物的大小,而不是它中的元素数量。更多的C ++ 11方法来做你正在做的事情:
#include <array>
#include <string>
#include <iostream>
int main()
{
std::array<std::string, 3> texts { "Apple", "Banana", "Orange" };
for (auto& text : texts) {
std::cout << text << '\n';
}
return 0;
}
ideone demo:http://ideone.com/6xmSrn
答案 3 :(得分:1)
sizeof(texts)
评估为96:数组及其字符串实例所需的字节数。
如其他地方所述,sizeof(texts)/sizeof(texts[0])
会给出您期望的值3。
答案 4 :(得分:1)
为数组添加一个停止值:
#include <iostream>
using namespace std;
int main ()
{
string texts[] = {"Apple", "Banana", "Orange", ""};
for( unsigned int a = 0; texts[a].length(); a = a + 1 )
{
cout << "value of a: " << texts[a] << endl;
}
return 0;
}
答案 5 :(得分:1)
如果你有一个非常简短的元素列表,你可以使用C ++ 11中引入的std::initializer_list和auto:
#include <iostream>
int main(int, char*[])
{
for(const auto& ext : { ".slice", ".socket", ".service", ".target" })
std::cout << "Handling *" << ext << " systemd files" << std::endl;
return 0;
}
答案 6 :(得分:1)
您需要了解std :: array :: size和sizeof()运算符之间的区别。如果您想循环以常规方式排列元素,则可以使用std :: array :: size。这将返回数组中的元素数量,但是如果您热衷于使用C ++ 11,则更喜欢下面的代码
for(const string &text : texts)
cout << "value of text: " << text << endl;
答案 7 :(得分:0)
怎么样:
username@prepatcher-oel7 impala-crypto-udf-master $ make
[ 50%] Building CXX object CMakeFiles/udfcrypto.dir/udf-crypto.cc.o
In file included from /home/username/impala-crypto-udf-master/udf-crypto.cc:27:0:
/home/username/impala-crypto-udf-master/sm3.h:23:24: error: expected unqualified-id before numeric constant
class BOTAN_PUBLIC_API(2,2) SM3 final : public MDx_HashFunction
^
/home/username/impala-crypto-udf-master/sm3.h:23:24: error: expected ‘)’ before numeric constant
/home/username/impala-crypto-udf-master/udf-crypto.cc:2133:1: error: expected ‘}’ at end of input
}
^
make[2]: *** [CMakeFiles/udfcrypto.dir/udf-crypto.cc.o] Error 1
make[1]: *** [CMakeFiles/udfcrypto.dir/all] Error 2
make: *** [all] Error 2
编译并与C ++ 11一起使用,并且没有“原始”循环:)
答案 8 :(得分:-1)
您可以按照以下步骤进行操作:
#include < iostream >
using namespace std;
int main () {
string texts[] = {"Apple", "Banana", "Orange"};
for( unsigned int a = 0; a < sizeof(texts) / 32; a++ ) { // 32 is the size of string data type
cout << "value of a: " << texts[a] << endl;
}
return 0;
}