为什么strstr() - char指针=数字?

时间:2018-02-08 15:10:06

标签: c++ pointers strstr

我有这个程序:

#include <iostream>
#include <conio.h>
#include <string.h>

using namespace std;

int main()
{
  char char1[30] = "ExtraCharacter", char2[30] = "Character", *p;

  p = strstr(char1, char2);
  cout << "p: " << p << endl;
  cout << "char1: " << char1 << endl;
  cout << "(p-char1): " << (p-char1) << endl;

  return 0;
}

当我运行它时,我得到:

p: Character
char1: ExtraCharacter
(p-char1): 5

正如所料。

但这不是问题,我不确定为什么"Character" - "ExtraCharacter"是一个整数(5)?也许不是整数,而是数字/数字。 实际上我不明白为什么“字符”存储在p中,而不是存储地址。

如果我从书中理解得很清楚,strstr()会返回内存地址,那么它是不是更像是一个奇怪的值,比如十六进制(0x0045fe00)或类似的东西?我的意思是,cout << p而不是cout << *p来显示该内存地址的实际值。

有人可以解释一下它的运作方式吗?

P.S。:如果标题不那么连贯,我道歉。

3 个答案:

答案 0 :(得分:6)

  

但这不是问题,我不确定为什么“Character” - “ExtraCharacter”是一个整数(5)?

您从另一个指针中减去一个指针,结果 - 数字,距离char char1指向char p指向的距离。这就是指针算法的工作原理。

注意:此减法仅在两个指针指向同一个数组(或最后一个元素后面)时有效,这在代码中就是这种情况,但您需要小心。例如,如果strstr()找不到susbtring,那么它将返回nullptr,并且您的减法将具有UB。因此,在减去之前至少检查p(并将nullptr传递给std::cout也会有UB)

  

如果我从书中理解得很好,strstr()会返回一个内存地址,它不应该更像是一个奇怪的值,比如十六进制(0x0045fe00)或类似的东西吗?我的意思是,它是cout&lt;&lt; p not cout&lt;&lt; * p显示该内存地址的实际值。

p是一个指针,也就是记忆地址。 std::ostream有特殊规则如何打印指向char的指针 - 作为字符串,因为C中的字符串以这种方式存储。如果你想把它看成一个指针,只需投射它:

std::cout << static_cast<void *>( p );

然后你会把它看作一个地址。

答案 1 :(得分:1)

要显示地址,您必须将char*投射到void*

std::cout << "p: " << static_cast<const void*>(p) << std::endl;

Demo

答案 2 :(得分:1)

对于std :: basic_ostream(cout的类型),字符和字符串参数(例如,char或const char *类型)由运算符&lt;&lt;的非成员重载处理。被视为字符串。 char [30]将被衰减为const char *参数,basic_ostream将在指针的地址处输出以null结尾的字符串。

对于(p-char1),减去两个指针的结果是std :: ptrdiff_t。它是一个实现定义的有符号整数。这就是输出为5

的原因