C++ 初等C++;类型混淆

C++ 初等C++;类型混淆,c++,types,constructor,C++,Types,Constructor,我正在阅读,我注意到当作者使用string类时,构造函数会执行如下函数调用: string::string(const char* str) { initializeFrom(str, str + strlen(str)); } 如果initializeFrom函数接受两个char*参数,那么第二个参数如何能将(char*+int)传递给char*并使其正常工作?类型系统如何解释此语句 提前感谢。这就是所谓的指针算术。char*+int会产生一个char*,即内存中较高的int个字符。

我正在阅读,我注意到当作者使用string类时,构造函数会执行如下函数调用:

string::string(const char* str) {
    initializeFrom(str, str + strlen(str));
}
如果initializeFrom函数接受两个char*参数,那么第二个参数如何能将(char*+int)传递给char*并使其正常工作?类型系统如何解释此语句


提前感谢。

这就是所谓的指针算术。char*+int会产生一个char*,即内存中较高的int个字符。

第一个参数指向char数组的开头,第二个参数指向char数组末尾的NULL char

const char *str = "abc";
char *start = str; // start now points to the first char.
char *end = str + strlen(str); // end now points to the null char at the end.
您可以通过打印来确认这一点:

printf("%c %d",*start,*end); // will output: a 0
为什么第二个参数可以传递(char*+int)


它仍在传递一个指向strlen(str)的
char*
经过最初指向的位置。

请记住,指针只是一个保存内存地址的变量。因此,您可以向内存地址添加值。内存地址是一个数字

当您向特定类型的指针添加1时,它实际上会添加1*sizeof(type)。当您添加任何值N时,它实际上会添加N*sizeof(type)

考虑以下示例:

int x[5] = {0,1,2,3,4};
int *p = &(x[0]);//point to the first element
p = p + 1;//p now points to the second element.

当一个参数是指向任何完整类型的指针(例如,
T*p
)而另一个参数是整数(例如,
i
)时,可以使用二进制加法运算符
+
-
)。它们实现了所谓的指针算法

编译器假定指针指向某个数组的元素(例如,
T数组[N]
)。该操作生成一个指向数组另一个元素的指针,该元素是远离原始元素的
i
元素。可以沿任意方向“移动”指针,即指向数组的开头或数组的结尾。例如,如果
p
指向
array[3]
,则
p+4
将指向
array[7]

该操作仅在结果指向数组的现有元素或数组最后一个元素之后的元素时有效,即给定数组
T array[N]
,可以创建指向从
array[0]
到虚拟元素
array[N]
的元素的指针。任何使用指针算术跨越这些边界的尝试都会导致未定义的行为

类型
T
必须完整,这意味着指针算法不能与
void*
指针一起使用,例如,即使某些编译器允许将其作为扩展(将
void*
指针视为等同于
char*
指针)

除了二进制加法运算符外,指针算术还包括前缀和后缀一元运算符
++
-
运算符(应用于指针)以及复合赋值运算符
+=
-=
(指针在其左侧,整数在右侧)


在您的情况下,
str+strlen(str)
表达式将生成一个
char*
类型的指针,该指针指向字符串
str
中终止的
\0
字符。我认为这可能回答过度了

在:

str
是指向字符串开头的指针

(str+strlen(str))
是指向字符串结尾的指针


请记住,
str
(字符指针)只是一个整数(
(int)
(long)
(long-long)
,取决于体系结构),用于标识内存中的位置。

如果
int
为-ve,则内存中的值也可能较低;因此,它应该是一个
无符号int
,以便结果在内存中始终更高。[如果这是吹毛求疵的话,很抱歉;]@legends2k这是真的,尽管strlen()永远不应该返回负值,因此这里分析的特定代码将导致第二个参数始终大于或等于第一个参数。
strlen()
永远不会返回负数。它根本不能;它返回一个size\u t,这是一个无符号类型。
strlen()
实际上返回一个
size\u t
,而不是
int
。其中一个重要区别是
size\u t
是一种无符号类型,即它只能容纳正数。这是有意义的——字符串长度可以是0、1或30000个字符,但决不能是-7。指针(并不总是)是整数。例如,在x86-16上,它是一对整数。
 initializeFrom(str, str + strlen(str));