我很难理解字符串作为指针。显然,字符串被理解为指向字符串的第一个地址的指针。所以使用“&” - 运算符我应该收到字符串第一个字符的地址。这是一个小例子:
#include "stdafx.h"
#include <iostream>
using namespace std;
int main(){
char text[101];
int length;
cout << "Enter a word: ";
cin >> text;
length = strlen(text);
for (int i = 0; i <= length; i++) {
cout << " " << &text[i];
}
return 0;
}
当输入诸如“Hello”之类的单词时,输出为:“Hello ello llo lo o”。相反,我希望收到“Hello”的每个字符的地址。当我使用演员long(&text[i])
时,效果很好。但我不明白为什么。没有强制转换,显然“&amp;” - 运算符给出了要打印的字符串的起始地址。使用强制转换,它分别给出每个角色的地址。
也许某人可以向我解释一下 - 我真的很感激!
答案 0 :(得分:4)
&text[i]
相当于text + i
,并使用指针算法将指针沿着char[]
数组移动i
个位置。效果是在第(i)个字符上启动cout
,调用<<
到const char*
的重载。这将输出从起始点到NUL终止符的所有字符。
text[i]
但是char
类型,调用<<
到char
的重载。这会输出一个字符。
在C ++中,如果需要字符串,请改用std::string
。如果cin >> text;
是text
类型,您仍然可以写std::string
!您的代码也不容易超出您的char
缓冲区。
答案 1 :(得分:3)
要打印数组元素的地址,您可以这样做:
cout << " " << (void*)&text[i];
此:
cout << " " << &text[i];
相当于:
cout << " " << text + i;
表示您要求从索引i
开始打印字符串。
答案 2 :(得分:3)
如果您有一个存储字符串的字符数组,例如
char text[] = "Hello";
然后将数组初始化为
char text[] = { 'H', 'e', 'l', 'l', 'o', '\0' };
在本声明中
std::cout << text;
对operator <<
类型使用了const char *
重载,并且数组text
被隐式转换为指向其第一个元素的指针。
您可以改为编写
std::cout << &text[0];
因为在两个语句中,表达式text
和&text[0]
的类型为char *
。
为类型const char *
重载的运算符输出从指针地址开始的字符,直到遇到零字符。
所以如果不是语句
std::cout << &text[0];
你要写
std::cout << &text[1];
然后唯一改变的是字符串的起始地址,仅此而已。实际上,您输出的字符串表示为
{ 'e', 'l', 'l', 'o', '\0' }
如果要写
std::cout << &text[2];
即如果表达式右侧的指针向右移动一个位置,则意味着您将处理字符串
{ 'l', 'l', 'o', '\0' }
等等。
这是operator <<
重载像
template<class traits>
basic_ostream<char, traits>& operator<<(basic_ostream<char, traits>&,
const char*);
只输出第二个参数指向的实体作为字符串。
如果要输出指针本身的值而不是指针所指向的字符串,则应使用另一个重载的operator <<
声明为
basic_ostream<charT, traits>& operator<<(const void* p);
Tp调用它你应该编写例如
std::cout << ( void * )text;
或
std::cout << ( void * )&text[i];
其中i
是某个索引。
您可以使用像
这样的C ++强制转换代替C转换std::cout << static_cast<void *>( &text[i] );