c++数组问题

Posted

技术标签:

【中文标题】c++数组问题【英文标题】:c++ array question 【发布时间】:2010-07-14 06:09:33 【问题描述】:

我想初始化一个大小为 200 的双精度数组,它的值是 c++ 中索引 0 到 199 的 0 到 199。 我知道我可以通过一个简单的 For 循环来做到这一点,但是有没有办法像这样初始化双精度数组?

谢谢

【问题讨论】:

见How to fill a vector with non-trivial initial values?。其他几个选项包括 iota(非标准)和 Boost 的 counting_iterator。 @Matthew:哇,我从来不知道counting_iterator。您应该将其添加为答案,否则我将窃取它。 :) 【参考方案1】:

不是真的。 for 循环是您的最佳选择:

double array[200];
for(int i = 0; i < 200; i++)
    array[i] = static_cast<double>(i);

【讨论】:

这是唯一的答案,我想。即使是 c++ 新手也会毫不费力地理解它。其他答案(std::generate、counting_iterator 等等)是为了展示 c++ 的技巧,而不是解决实际问题。代码应该尽可能简单(但不是更简单)=) @Sad:counting_iterator 的解决方案很简单。 @Sad:这样的项目很糟糕。标准库是语言的一部分;使用失败表示程序员在 C++ 中编程失败。应该在允许的情况下使用 Boost,尽管这对某些人来说并不总是可行的。 (再说一遍,您可以轻松提取单个库。)对std::copy 缺乏了解是无法判断C++ 代码,因为一个人不是C++ 程序员。 @SadSido:在一定程度上我同意 GMan。每个程序员都需要一个经过调试的高性能库来进行基本操作。不管那个图书馆实际上是什么。例如,EA Games 使用 EASTL,它使用专用分配器以及分配和初始化策略来实现更高的性能。但我想说没关系:我希望任何 C++ 程序员都能够在互联网上搜索并了解当我使用一些 STL 或 Boost 部件时发生了什么,就像这里提到的那样简单(我不是在说boost::mpl )。 @SadSido:你可能不喜欢它,但 GMan 是对的。 C++ 是语言加上标准库,并且非常强调后者。使用循环的甚至不到六个答案中的一个一开始就出错了循环,这说明了为什么循环并不优越。【参考方案2】:

这是std::generate的一种方式:

template <typename T>
class nexter

public:
    nexter(T start = T())
        : value_(start)
    
    

    T operator()()
    
        return value_++;
    

private:
    T value_;
;

int main()

    double data[200];
    std::generate(data, data + 200, nexter<double>());

如果你使用的是 C++0x,你可以跳过仿函数:

int main()

    double data[200];
    double next = 0.0;
    std::generate(data, data + 200, [&next]()  return next++;  );

【讨论】:

严格来说,我认为for_each 实际上并不打算改变元素。此外,如果您想忽略一个参数,请不要命名它。最后,如果您要使用仿函数,不妨使用std::generate。 :) @GMan - 谢谢,我忘记了 std::generate - 更新了我的示例,还给出了一个使用 C++0x lambdas 的示例。 @RSamuel:+1 很好,C++0x 解决方案可以说是迄今为止最干净的。 (如果只有标准库使用该死的范围而不是迭代器!)为了记录,-1 不是我。 @GMan - 谢谢。而且我等不及 lambda 不被认为是最先进的,因为它们非常好用。 +1 但只是为了展示一个不错的 C++0x lambda。函子版本是...不,请。不要那样做。【参考方案3】:

使用counting_iterator

const int SIZE = 200;
double array[SIZE];
std::copy(counting_iterator<int>(0), counting_iterator<int>(SIZE), array);

【讨论】:

恕我直言,::std:;copy 应该被编写为要求目标开始和结束,源开始而不是相反。无论哪种方式,您都可以获得缓冲区溢出,但当溢出只是读取而不是写入时,更难利用。 @Omnifarious:更好的是,两者都需要;)但我同意阅读溢出不太可能导致问题。 像 GMan 我不知道这个小奇迹。如此简单实用!【参考方案4】:

与anthony-arnold 相同,但使用 C++ 向量(或列表或双端队列):

std::vector<double> array ;
array.reserve(200) ; // only for vectors, if you want
                     // to avoid reallocations

for(int i = 0; i < 200; i++)
    array.push_back(i) ;

【讨论】:

【参考方案5】:

如果数组的所有值都相同,则可以轻松完成。但是价值观是不同的,所以我不认为你直接这样做。

double array[200];

for(int i=0 ; i<200 ; i++)  
    array[i] = (double)i; 

【讨论】:

您的代码在i = 200 时会导致无效的内存访问,因为它将写入array[200]。将array[i] 的赋值放到它所属的for 语句的主体中! 哦,此外,array[0] 没有写入并且保持未初始化状态。 我不认为 c++ 的机制如何。如果它从左侧解析句子,则没有任何无效的内存访问。 for 循环结束,直到“array[i] = (double)i” 对不起。我认为它在执行 "i++ , array[i] = (double)i" 之后检查条件。我想它会在 i++ 和条件等每个操作之后检查。 @Judas:不,它会在分配后进行检查。【参考方案6】:

如果200 是一个固定常量并且您不想要运行时开销,我基本上看到了两种解决方案。

对于 C 解决方案,您可以通过预处理器解决它。在认为 Boost 有预处理器 for 循环这样的事情。这样做的好处是可以在编译时完成,完全没有运行时开销。

对于所有编译器/预处理器来说,常量 200 本身可能有点大,但大多数现代编译器/预处理器应该能够处理这个问题。

我认为,对于 C++ 解决方案,您可以使用 template 元编程来实现。具有template 参数中元素数量的递归类型可以解决问题。但是对于这么大的常量,编译时间开销可能会令人望而却步。

【讨论】:

有趣的选项,但没有一个比循环更容易被调用。尤其是模板递归是一个很难理解的东西 @Elemental:取决于对谁来说更简单。如果你有一个通用的宏来做这件事,那么调用端就会变得非常简单,比如double A[] = INIT_DARRAY(200);。当然,这样一个宏的实现并不简单,但这确实是硬币的另一面。并且这样的宏是否隐藏了真正的宏定义 à la Boost 或递归模板在这方面并不重要。【参考方案7】:

初始化数组值的唯一方法是在声明点(如果初始化器小于数组,则所有其他元素都初始化为零;

double arr[5] = 0, 1, 2; // arr = [0.0 ,1.0 ,2.0 ,0.0 ,0.0]

否则无法初始化值,您将不得不遍历数组。

所以你可以做的是:

double arr[] = 0, 1, 2, 3, /* ... */, 199; 

虽然循环会更好在大多数情况下

【讨论】:

与循环表示法相比,另一个优点是可以在编译时解决。缺点是写起来很痛苦...... @paercebel,当然,它是在编译时完成的,这是 only 的优势。至于写它,我会用脚本生成一次,以免出错。【参考方案8】:

我认为 for-loop 是最适合您的情况的最简单和最合适的解决方案。如果您只想知道另一种方法,可以使用std::transform

#include <vector>
#include <algorithm>

double op_increase (double i)  return static_cast<double>(static_cast<int>(i)+1); 

int main() 
 
    std::vector<double> x( 200 ); // all elements were initialized to 0.0 here
    std::transform( x.begin(), x.end()-1, x.begin()+1, op_increase );

    return 0; 
 

【讨论】:

以上是关于c++数组问题的主要内容,如果未能解决你的问题,请参考以下文章

C++ 函数返回数组

将指针数组传递给函数指针数组的 C++ 问题

c++数组问题

C++动态申请数组问题

多维数组索引 C++ 中的多维数组

C++ 与 C# 数组性能问题