C分配-为什么VisualStudio2019要求我分配内存而代码块没有?

C分配-为什么VisualStudio2019要求我分配内存而代码块没有?,c,visual-studio-2019,dynamic-memory-allocation,allocation,C,Visual Studio 2019,Dynamic Memory Allocation,Allocation,我正在努力学习使用可视代码。 我的问题是,当我运行一个代码时,我得到了这个错误消息,“expected constant expression”,而当我在代码块中运行相同的代码时,函数工作没有问题 通过谷歌搜索,我了解到我需要为这行代码分配内存 怪物温度[l2+h2] 我的问题是,我该如何处理这一行?为什么VisualStudio2019要求我分配内存而代码块不是 void m_s_m(monster *list, int l1, int h1, int l2, int h2, int *com

我正在努力学习使用可视代码。 我的问题是,当我运行一个代码时,我得到了这个错误消息,“expected constant expression”,而当我在代码块中运行相同的代码时,函数工作没有问题

通过谷歌搜索,我了解到我需要为这行代码分配内存
怪物温度[l2+h2]

我的问题是,我该如何处理这一行?为什么VisualStudio2019要求我分配内存而代码块不是

void m_s_m(monster *list, int l1, int h1, int l2, int h2, int *comparisons, int *copies, int *block_copies, int *mallocs, int use_name, int use_weight)
{
    monster temp[l2+h2];
    int index = l1;
    int k=l1;
    (*mallocs)++;
    (*block_copies)++;
    while(l1<=h1 && l2<=h2)
    {
        (*comparisons)++;
        if(use_name == 1)
        {
            if(strcmp(list[l1].name, list[l2].name)<0)
            {
                (*copies)++;
                temp[index] = list[l1];
                l1 = l1++;
            }
            else
            {
                (*copies)++;
                temp[index] = list[l2];
                l2 = l2++;
            }
        }
        if(use_weight == 1)
        {
            if(list[l1].weight<list[l2].weight)
            {
                (*copies)++;
                temp[index] = list[l1];
                l1 = l1++;
            }
            else
            {
                (*copies)++;
                temp[index] = list[l2];
                l2 = l2++;
            }
        }
        index++;
    }
    if(l1>h1)
    {
        (*block_copies)++;
        while(l2<=h2)
        {
            (*copies)++;
            (*comparisons)++;
            temp[index] = list[l2];
            index++;
            l2++;
        }
    }
    else
    {
        (*block_copies)++;
        while(l1<=h1)
        {
            (*copies)++;
            (*comparisons)++;
            temp[index] = list[l1];
            index++;
            l1++;
        }
    }
    (*block_copies)++;
    while(k<index)
    {
        (*copies)++;
        list[k]=temp[k];
        k++;
    }

}

void m_s_m(怪物*列表、int l1、int h1、int l2、int h2、int*比较、int*拷贝、int*块拷贝、int*mallocs、int use_名称、int use_权重)
{
怪物温度[l2+h2];
int指数=l1;
int k=l1;
(*mallocs)+;
(*块拷贝)+;

而(l1有两个问题

monster temp[l2 + h2];
首先,它是一个可变长度数组(VLA)。最初,C要求您使用常量数组大小,因为编译器需要知道数组将占用多少内存。但在C99中,根据流行的要求,C允许使用在函数执行之前未知的大小声明本地数组。事实上,一个函数调用和下一个函数调用之间的大小可能不同,这是这就是为什么它们被称为可变长度。VLA是C11的可选功能,主要是因为Microsoft不愿意实现它们。而且Microsoft从未实现过它们。因此,您不能将它们与Microsoft C编译器一起使用

大多数其他C编译器都完全可以使用它们,我想您的代码块安装使用的是Microsoft编译器以外的其他C编译器。但仅仅因为您可以使用VLAs并不意味着这是一个好主意。您应该只在堆栈上分配数组(无论是固定长度还是可变长度)如果你确定它可以放在堆栈上。这很棘手,因为你无法知道堆栈有多大,但可以合理地假设堆栈足够大,可以容纳几个短数组。除了在“桌面”上,甚至没有办法给你一个指导方针在操作系统中,几乎可以肯定的是,你可以通过数千个元素逃脱惩罚。数百万个元素在自找麻烦

VLAs的问题是,你真的不知道数组会有多大。如果数组声明是编译时常量,有人可能会过来对你说,“是的,一个12整数的数组就可以了”,或者“wtf,你正试图在堆栈上增加1亿个双倍。”但是对于VLAs,没有人知道。很有可能有一天,你会使用太大的数组运行该程序,它会崩溃或打开你的计算机,导致恶意接管或类似情况。排序函数往往会使用大数组调用

所以,是的,最好是malloc,即使编译器不强迫你这么做

这是一个问题。另一个问题是
l2+h2
不能是有效的数组大小。我真的不知道
l2
h2
是什么(正如我在一篇评论中所说,使用这样的变量名就像写一本小说,里面有20个不同的字符都被命名为“Sue”),但我可以猜测它们都是被排序数组中的索引。将两个索引相加是完全没有意义的行为。(有意义的和是起点和长度,而不是起点和终点。)


因此,除了
temp
是一个VLA之外,它的大小还没有被正确计算。

1.如果你想让其他人阅读你的代码,试着使用更有意义的变量名。2.你的代码中根本没有malloc,所以我不知道
mallocs
计算的是什么。3.保持一致。写“向x添加一个”的最佳方法是
++x
,但是
x++
x+=1也可以。但是在程序中只能使用其中一个,除非你有很好的理由。