数组在C上默认是可变长度的吗?
我试图制作一个基于数组的线性列表,然后我编译了以下内容:数组在C上默认是可变长度的吗?,c,arrays,memory-management,gcc,C,Arrays,Memory Management,Gcc,我试图制作一个基于数组的线性列表,然后我编译了以下内容: char size = 0; char testarray[10]; int main() { add('a'); add('b'); add('c'); add('d'); add('e'); add('f'); add('g'); add('h'); add('i'); add('j'); add('k'); add('l'); add('m'); add('n'); add('o');
char size = 0;
char testarray[10];
int main() {
add('a'); add('b'); add('c');
add('d'); add('e'); add('f');
add('g'); add('h'); add('i');
add('j'); add('k'); add('l');
add('m'); add('n'); add('o');
print();
return 0;
}
void add(char newchar) {
testarray[++size] = newchar;
}
void print() {
char i = 0;
for (i = 0; i <= size; i++) {
printf("%c ", testarray[i]);
}
}
char size=0;
char-testarray[10];
int main(){
添加('a');添加('b');添加('c');
add('d');add('e');add('f');
添加('g');添加('h');添加('i');
添加('j');添加('k');添加('l');
添加('m');添加('n');添加('o');
打印();
返回0;
}
void add(char newchar){
testarray[++size]=newchar;
}
作废打印(){
字符i=0;
对于(i=0;i否,它们的大小不是可变的。您只是在写入数组末尾的内容并填充其他内存。只是没有任何检查来证明这一点。否
想象一下C语言是世界上最棒的汇编语言,它也是可移植的。它完全不同于设计为内存安全的语言(这将是大多数其他语言)
回答这样的问题的一种方法是使用cc-S…
编译并检查生成的汇编代码。即使您不熟悉机器语言,也可能知道它没有调用或检查下标范围
C不能真正做到这一点,因为x[i]
被定义为*(x+i)
,所以它真的像他们说的那样是一种“高级汇编语言”。正如Vaugh所说,你只是“幸运”*通过数组的内存是可写的。有可能出现分段错误。事实上,如果您稍微更改程序,使数组位于堆栈上,然后通过valgrind运行它,它将向您发出大量警告
*“幸运”因为程序没有崩溃。不幸的是…它会在以后崩溃。只要你在为应用程序分配的范围内,你就可以在任何地方使用指针/地址。继续走到足够远的地方,你要么扔掉你的程序,要么撞到分配内存的边缘,并得到某种保护故障。运行时检查iIt’那太贵了,反正我也不想买
交换两个变量
char testarray[10];
char size = 0;
看看当你运行它时会发生什么
然后这样做:
char size = 0;
char testarray[10];
char stuff[10];
在开始向testarray添加内容之前,先初始化内容,然后在完成之后打印内容[]数组。您应该看到溢出。在C中,将非数组变量放在赋值列表的第一位是一个很好的规则,数组放在最后,这样您就有更好的调试机会。…而且他正在导致未定义的行为,这意味着任何事情都可能发生,从看似有效到点燃气氛,再到用C购买比萨饼信用卡。所以这毕竟是危险的。哦,好吧,谢谢。我想我有点太习惯于Java的过度保护。正如有人在休息室(有点开玩笑地)所说,“C++拥有汇编语言的所有功能和…汇编语言的所有便利。”@SethCarmegie-注意,正如C中使用的术语,“可变长度数组”仍然有一个静态大小—每次调用函数时,只需在运行时确定一个大小(每个调用可能不同,但在整个调用过程中保持不变,之后数组将超出范围)。