【问题标题】:Arrays created in functions,compile time or run time?在函数、编译时或运行时创建的数组?
【发布时间】:2018-11-07 11:15:55
【问题描述】:

当我们在堆栈上创建一个数组时,大多数编译器都想知道数组的大小,这将在编译时确定,所以通常我们不能让用户从标准输入中输入数组的大小,但是如果我们调用一个函数并将用户输入的数字传递给一个函数来创建一个数组怎么办?

这个函数不是在编译时调用的吗?

例如,如果用户输入 1,这个函数不是在运行时被调用吗? 由于用户将决定是否调用该函数。

或者这仍然是编译时间?

#include <iostream>

void someFunction(int number){

    int sampleArray[number];

    for(int i = 0; i < number; i++){

        sampleArray[i] = 0;
    }
    // I know what I'm doing is pointless but is it possible?
}

int main()
{
   int number = 0;
   int choice = 0;

   std::cout << "do you want to create an array? press 1 for yes" << std::endl;
   std::cin >> choice;
   if(choice == 1){

   std::cout << "enter size" << std::endl;
   std::cin >> number;

   someFunction(number);

   }
}

【问题讨论】:

  • 编译时不调用任何东西。
  • 使用return sampleArray;,返回局部变量的地址,以及悬空指针。
  • 非常好的观点

标签: c++ c++11 variable-length-array


【解决方案1】:

您使用的是可变长度数组。它不是 C++ 标准的一部分,但一些编译器支持它作为扩展。

为了使您的代码符合标准,请不要使用它。请改用std::vector&lt;int&gt;

std::vector<int> someFunction(int number){

    std::vector<int> sampleArray(number);

    // No need for this. sampleArray elements are zero initialized.
    /*
    for(int i = 0; i < number; i++){
        sampleArray[i] = 0;
    }
    */
    return sampleArray;
}

【讨论】:

    【解决方案2】:

    number 不是 constexpr 值。

    所以,int sampleArray[number]; 仍然不是有效的 C++ 并且是 VLA 扩展。

    【讨论】:

      【解决方案3】:

      在您展示的情况下,在 C(和大多数 C++ 编译器)中,当调用函数时,数组的空间会保留在堆栈中。

      同样,您可以使用 alloca() 等函数手动完成。

      【讨论】:

      • VLA 和 alloca() 不是 C++ 的一部分。
      【解决方案4】:

      你正在做的是创建一个可变长度数组,这通常是一个不好的做法,如果你想静态创建你的数组,最好给它一个固定长度的值,否则如果你急需可变长度数组,您可以使用动态分配来制作数组,也可以使用 STL 中的向量。

      【讨论】:

      • 这不仅是不好的做法,而且在 C++ 中也是不允许的。
      【解决方案5】:

      我认为将动态内存管理命名为更正确的名称。另外我真的怀疑你给出的示例代码是否能正常工作。 举个例子:

      int sampleArray[number]; 
      

      也会导致很多编译器出错,最终你还是会在其他编译器中得到警告。

      您不必使用函数来初始化具有不同大小的数组。你可以简单地用一个指针来做:

      int size;
      std::cin >> size;
      int * array = new int[size];
      

      这适用于我所知道的任何编译器,也不会引起警告。 但是您必须记住,当您不再需要数组时,您将不得不删除内存。就像它即将超出范围一样。

      delete []array;
      

      从 C++ 11 开始,您可以使用智能指针。那些将代替您处理数组内存并将删除内存。

      int size;
      std::cin >> size;
      std::shared_ptr<int[]> array(new int[size]);
      

      unique_ptr 等也可以这样做。 在许多情况下,将 std::vector 用于任何 int 数据类型存储就足够了。

      【讨论】:

      • 更喜欢std::unique_ptr 而不是std::shared_ptr,因为您总是希望找到最窄、监管最严格的解决方案。对于此任务,首选 std::vector 而非两者。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-11-19
      • 2018-03-16
      • 2022-11-28
      • 1970-01-01
      • 2011-05-08
      • 1970-01-01
      相关资源
      最近更新 更多