下面的代码我试图执行指针算术
#include <stdio.h>
#include <stdlib.h>
int main() {
int *ptr = malloc(100);
printf("base : %p\n", ptr);
printf("\n");
printf("base+1 : %p\n", ptr+1);
ptr+= 100;
*ptr = 90;
printf("addr: %p val : %d\n", ptr, *ptr);
return 0;
}
输出:
base : 0x5621e46412a0
base+1 : 0x5621e46412a4
addr: 0x5621e4641430 val : 90
提问:
- return(100);它会返回100字节吗?
1.这里我没有类型转换malloc的返回地址,顺便说一句,malloc将返回void类型正确的ptr+1如何递增4字节?
1.现在增加ptr+100,所以400字节将得到正确的增加?我也可以分配值与出分段故障它是如何工作的?
试图理解在这种情况下指针算术是如何工作的
3条答案
按热度按时间oug3syen1#
return(100);它会返回100字节吗?
是的。或者更准确地说:它将为您保留100个字节,并返回该内存区域的地址。
这里我没有类型转换malloc的返回地址,顺便说一句,malloc将返回void类型正确的ptr+1如何递增4字节?
这是不正确的。
malloc
不返回void
,而是返回指向void
的指针。这与任何指向任何数据的指针兼容,而无需强制转换。在分配给ptr
之后,它是指向int
的指针。增量仅取决于指针的类型,即int
。现在增加ptr+100,所以400字节将得到正确的增加?我也可以分配值与出分段故障它是如何工作的?
正确(假设您似乎在使用32位系统)。这意味着您正在非法访问您不拥有的内存,并且您不应该访问。这会导致未定义的行为。它可能看起来工作或崩溃。未定义的行为也意味着它没有定义为导致segfault。
参见Undefined, unspecified and implementation-defined behavior
xienkqul2#
malloc(100)
将返回一个指针,指向已保留100字节内存的位置,或者返回一个空指针。1.这里我没有对malloc的返回地址进行类型转换,...
简单赋值运算符(
=
)自动将其右操作数转换为左操作数的类型。当左操作数是指针时,右操作数可以是以下任意一种:void
的指针,但右类型可以省略左类型具有的限定符或顺便说一句,malloc将返回void类型,正确的ptr+1如何递增4字节?
C不“记得”来自
malloc
的返回类型为void *
的地址。当计算ptr+1
时,ptr
的类型用于算术。ptr
的类型为int *
,因此算术以int
为单位执行。1.现在增加ptr+100,所以400字节将得到增加正确吗?
在分配的空间内,如果C实现为
int
使用4个字节,则添加 x 将向地址添加4x 个字节。在分配的空间之外,C标准没有定义指针算术的行为。如果分配的空间是1000字节而不是100字节,则ptr+100
将计算超出起始400字节的地址。...也我可以能够分配值与出分割故障它是如何工作的?
内存保护通常以页面为单位工作。如果您使用的内存位于您可以访问的页面内,即使它不是您应该访问的页面中的位置,也不会出现分段错误。或者,如果您计算错误的地址,结果仍然是您可以访问的页面,内存保护不能绝对防止进程的所有地址错误,并且动态分配的内存可能位于允许程序访问的具有许多页的区域中。
bvuwiixz3#
1.否;它将返回一个指向至少100个字节的 * 指针 *,或
NULL
。1.否;它以
sizeof(*ptr)
递增,在本例中为sizeof(int)
。这可能是一个不同于4的值。ptr-to-void与任何没有强制转换的对象指针都是赋值兼容的,在C中,最好不要强制转换malloc返回值。搜索这个网站了解原因。1.不正确;它以
100*sizeof(*ptr)
递增。这可能是400以外的值。通过该指针写入是 * 未定义的行为 *,因此任何事情都可能发生,包括没有明显的事情。要打印指针值,使用
%p
说明符是不够的,参数必须是指向void的指针,因此必须使用(void*)
强制转换,如