我想向后读取我的字符串。我这样做了,但是我不明白我的代码的两个部分是如何工作的。
char s1[] = "ABC";
printf("%s", s1);
size_t len = strlen(s1);
printf("\n%d", len);
char *t = s1 + len - 1;
printf("\n%s\n", t);
while (t>=s1)
{
printf("%c", *t);
t = t - 1;
}
t
如何指向字母C? len
和包含文字的数组?是因为指针t通过使用指针算术来添加其地址吗? 答案 0 :(得分:4)
此
char s1[] = "ABC";
看起来像
0x100 0x101 0x102 0x103 . . . .Assume 0x100 is base address of s1
--------------------------------
| A | B | C | \0 |
--------------------------------
s1
这里s1
是char数组,指向基地址0x100
(假设)。
我想反向读取我的字符串吗?
为此,您需要有人指向0x102
位置,即数组的最后一个元素
size_t len = strlen(s1); /* finding length of array s1 i.e it returns 3 here */
char *t = s1 + len - 1; /* (0x100 + 3*1) - 1 i.e char pointer t points to 0x102 */
编写了两行以上的代码。现在看起来像
0x100 0x101 0x102 0x103 . . . .
--------------------------------
| A | B | C | \0 |
--------------------------------
s1 t <-- t points here
现在,当您执行*t
时,它将在t
位置打印char值,即在0x102
处的值,即打印C
,在下一个迭代中,您需要打印将一个字符返回一个位置,因此您正在做t = t - 1;
。
注意:此处
char *t = s1 + len - 1;
s1
是字符指针,而len
是整数变量,因此在进行指针算术它会自动增加指针指向的数据大小。对于例如
char *t = s1 + len;
评估为
t = 0x100 + 3*sizeof(*s1); ==> 0x100 + 3*1 ==> 0x103
答案 1 :(得分:2)
char s1[] = "ABC";
s1
是由4个字符组成的数组char[4]
,值{'A','B','C','\0'}
size_t len = strlen(s1);
s1
从类型数组到类型指针的“衰减”(读取:自动转换)。因此s1
从4个字符的数组衰减为指向数组第一个字符的指针。
strlen
在遇到空字节定界符'\0'
之前先对字节数进行计数。从'A'
开始,我们可以算出'A'
,'B'
,'C'
。
C中的指针是普通整数(好的,在大多数体系结构上)。您可以添加它们并减去它们,并使用len = 3
将它们转换为整数。但是在不进行强制转换的情况下添加它们将使用“指针算术”,这意味着uintptr_t
的值等于(int*)5 + 2
。
5 + 2 * sizeof(int)
char *t = s1 + len - 1;
衰减到指向s1
数组中第一个字符即s1
的指针。我们添加'A'
,这意味着+ (len = 3)
指向s1 + 3
数组中保存'\0'
的字节。然后我们减去s1 = (char[4]){'A','B','C','\0'}
,因此- 1
现在指向在t
数组中包含字符'C'
的字节。
s1
开始:while (t >= s1) {
... *t ...
t = t - 1;
}
指向s1
。 'A'
指向t
。
而:'C'
大于t
。由两个。 s1
,即。 t - s1 = 2
循环:s1 + 2 = t
等于*t
。
减量:'C'
,所以现在t--
将指向t
。
而:'B'
大于t
。通过onw。
循环:s1
等于*t
。
递减:然后'B'
,所以现在t--
将指向t
。
while:现在'A'
等于t
。两者都指向数组的第一个字符。
循环:s1
等于*t
。
减量:然后'B'
,所以现在t--
将指向数组之前的未知位置。作为指针
(在大多数体系结构上)是简单的整数,您可以将其作为普通变量进行减量和增值。
同时:t
现在低于t
。循环终止。
注意:
s1
是未定义的行为,并产生nasal demons。使用printf("\n%d", len);
打印一个printf("\n%zu", len);
变量。size_t
说明符并强制转换为void %p
来打印指针值printf("%p", (void*)t)
。在数组中为数组之前的一个元素分配指针是C中的未定义行为。这发生在循环t = s1 - 1
的结束条件中。更改为t = t - 1
循环。答案 2 :(得分:1)
在语言中,C数组有点奇怪。在x数组处,可以很容易地退化为x指针。例如,如果传递给另一个例程,或者如您所愿,则添加到该例程。所以你是对的,它是指针运算。 (在指针算术中,您可以添加指针和整数以获取指针。)