【问题标题】:Dynamic Array Size in C++C++ 中的动态数组大小
【发布时间】:2015-06-02 19:10:16
【问题描述】:

我正在寻找一种方法来根据传递的参数动态设置整数数组的大小。 以伪代码为例:

int MyFunction(int number)
{
  int myarr[amount of digits in number];
}

因此,当输入为 13456 时,int array[] 的大小应为 5。 当我不知道大小的常量时,在 C++ 中执行此操作的最快方法是什么?

【问题讨论】:

  • 您不使用 std::vector 有什么原因吗?数组大小必须是编译时常量。您现在是在编译时调整大小还是仅在运行时调整大小?
  • int myarr[runtime_value] 是一个 VLA 扩展,无论如何都喜欢使用std::vector
  • 我只是想知道是否可以使用 siezof() 或类似的东西以某种方式动态分配整数的大小?我知道有 std::vector 但我想避免这种情况。
  • log10 可能会有所帮助,或者简单的std::vector::push_back 逐个数字。
  • 如果您按照sizeof 的思路进行思考,那么在大多数情况下,像int myarr[11]; 这样简单的东西就足够了(对于4 字节有符号整数)。这当然是最快的方法!

标签: c++ arrays dynamic int sizeof


【解决方案1】:

您不能创建具有运行时大小的数组,它必须在编译时知道。我会推荐std::vector

一种解决方案是在转换为字符串后对字符进行计数

#include <string>
int MyFunction(int number)
{
    std::vector<int> myarr(std::to_string(number).size());
}

在数学上,您可以取对数(以 10 为底)来查找数字中的位数。

#include <cmath>
int MyFunction(int number)
{
    int numDigits = static_cast<int>(std::log10(number)) + 1;
    std::vector<int> myarr(numDigits);
}

【讨论】:

  • 使用 log(10) 计算数字的位数是危险的。考虑非常大的数字和负数。使用 div 和 mod 循环数字更安全。
  • @CoryKramer 在 C99 中不正确,您可以创建运行时数组。看到这个答案stackoverflow.com/questions/737240/…
  • @jhilmer 这个问题是关于 C++,而不是 C。C++ 中运行时大小的数组只能通过编译器扩展获得,标准不允许。事实上,您发布的链接正是如此。
  • @CoryKramer 对不起,你是对的。它只是我的 gcc 有这个扩展默认启用。
【解决方案2】:

您可以做的另一个选择是通过直接访问数字的数字来完全避免使用数组:

unsigned int getDigit(unsigned int number, unsigned int index) {
  // See http://stackoverflow.com/questions/4410629/finding-a-specific-digit-of-a-number
}

unsigned int setDigit(unsigned int number, unsigned int index, unsigned int newVal) {
  // intPower is from the question linked to above.
  return number - get(number, index)*intPower(10, index) + newVal*intPower(10, index);
}

unsigned int size(unsigned int number) {
  // See http://stackoverflow.com/questions/1306727/way-to-get-number-of-digits-in-an-int
}

unsigned int push_back(unsigned int number, unsigned int newDigit) {
  // Assuming no overflow
  return 10*number + newDigit;
}

unsigned int pop(unsigned int number) {
  // Assume number != 0
  return number / 10;
}

这使您可以将您的号码视为一个数组,而无需实际初始化该数组。你甚至可以把它变成一个类并使用运算符重载来获得实际的数组语义。

【讨论】:

    【解决方案3】:

    您可以改用vector - 实际上我认为在这种情况下最好的选择。创建一个具有一些初始大小的向量。然后你可以动态增加它 -

    int initialSize = 5;                    
    vector<int> myvector(initialSize, 0);   //hold "initialSize" int's
                                           // and all initialized to zero
    myvector[0] = 567;                   // assign values like a c++ array
    

    【讨论】:

    • 这并不能解决他们确定有多少位数的主要问题。
    【解决方案4】:

    使用我的 gcc 版本 4.6.3,以下是可能的:

    int MyFunction(int number)
    {
        int myarr[int(ceil(log(number)))];
    
        ....
    
        return 0;
    }
    

    编辑:C99 这是有效的,请参阅:Array size at run time without dynamic allocation is allowed?

    【讨论】:

    • 这在 C++ 中是不允许的(没有编译器扩展)
    猜你喜欢
    • 2011-10-24
    • 1970-01-01
    • 2011-05-03
    • 2012-04-17
    • 2012-10-02
    • 2014-02-23
    • 2014-11-15
    • 2020-11-13
    相关资源
    最近更新 更多