了解处理变长数据,特别关注 C(99)

问题描述

以下是红龙书的摘录。处理程序活动记录中变长数据项的处理。

Pascal 在要求过程本地数组的长度可以在编译时确定的语言中几乎是独一无二的。更常见的是,本地数组的大小可能取决于传递给过程的参数的值。在这种情况下,在调用该过程之前无法确定该过程本地的所有数据的大小。

图 7.15 建议了一种处理可变长度数据的常用策略,其中过程 p 具有三个局部数组。这些阵列的存储不是 p 的激活记录的一部分;只有一个指向每个数组开头的指针出现在活动记录中。这些指针的相对地址在编译时是已知的,因此目标代码可以通过指针访问数组元素。

Figure

图 7.15 中还显示了一个由 q 调用的过程 pq 的活动记录在 p 的数组之后开始,q 的变长数组在此之后开始。

在上面摘录的第一部分,文本讨论了 Pascal 编程语言的特性,然后他们讨论了相同的可能实现。现在我不熟悉Pascal,想了解C中处理情况的方式。

我知道可以使用 C 及其姊妹函数在 malloc 中动态创建数组,这会导致在堆上分配内存,并将指向第一个字节的指针返回给我们。完全不是问题。

如果我们在 C 中创建数组,其中数组的大小是一个常量:

int function() {
   int a[100];
  }

然后将数组放置在如下所示的激活记录的local data部分:

activation record

在上面的例子中,数组 a 的大小在编译时就知道了。没有问题。

现在的情况:“更多情况下,本地数组的大小可能取决于传递给过程的参数的值。在这种情况下,无法确定过程本地的所有数据的大小直到调用该过程。”

案例 1:

现在让我们考虑下面的代码:

  int function(int n){
           int a[n];
  }
  int main() {
        function(10);
  }

现在在上面的情况下,n 的参数 function 的大小可以在编译时知道,因此数组 a 的大小虽然变量可以在编译时知道时间。有了这个逻辑,C 是否会按照龙书a 中所示的方式分配上面的数组fig 7.15

情况 2:

  int function(int n){
           int a[n];
  }
  int main() {
        int x;
        scanf("%d",&x);
        function(x);
  }

现在在上面的情况下,参数nfunction的大小只能在运行时知道(?)还是还是上面的情况,即在编译时已知? 现在在这段代码中,数组 a 被分配到哪里。堆还是栈?

我去了 hereherehere 但没有找到我要找的解释...


这里我说的是 C99

解决方法

暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!

如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。

小编邮箱:dio#foxmail.com (将#修改为@)