C ++ char массив со стандартным вводом - PullRequest
1 голос
/ 18 декабря 2008

Я пытаюсь получить размер массива, заполненного stdin:

char *myArray;
cin >> myArray
cout << sizeof(myArray);

Возвращает 4, когда я ввожу строку, длина которой больше 4, например "40905898"

Где я иду не так?

Ответы [ 8 ]

11 голосов
/ 18 декабря 2008
Оператор

sizeof статически оценивает размер объекта, который вы ему передаете. char* - указатель, который в зависимости от архитектуры машины имеет определенный размер (4 байта в 32-битных системах и 8 байтов на 64-битных машинах). Чтобы выполнить то, что вы пытаетесь сделать, я предлагаю вам использовать тип string, который вы можете использовать, добавив #include <string> вместе с using namespace std; в ваш исходный файл.

string line;
cin >> line;
cout << line.length() << endl;

Это менее подвержено ошибкам и проще в использовании.

Кстати, то, что вы пытались сделать, действительно опасно. Фактически, когда вы используете cin >> myArray, вы уже должны были выделить часть памяти для myArray, чего вы еще не сделали. Это приведет к повреждению памяти, что может привести к сбою в работе вашей программы и, возможно, подвергнуть ее атакам переполнения.

Простой массив в C ++ не имеет представления о его размере. Вы можете использовать sizeof только в том случае, если массив статически размещен , и вы используете sizeof для самого массива, а не другой указатель на него, например, это не будет работать, как вы могли ожидать:

int x[5];
int *a = &x[0];
// a[i] is now the same as x[i] but:
cout << sizeof(x) << endl; // prints 20, assuming int is 32 bits long
cout << sizeof(a) << endl; // prints 4, assuming a pointer is 32 bits long

Обратите внимание, что общий размер массива напечатан в первой строке, а не количество элементов. Вы можете использовать sizeof(x)/sizeof(*x), чтобы узнать количество элементов в статических массивах. Это невозможно для динамически размещаемых массивов, использующих new. На самом деле массивы C ++ очень подвержены ошибкам, и вы должны быть предельно осторожны при работе с ними, и вместо них лучше использовать vector и string.

2 голосов
/ 18 декабря 2008

sizeof (указатель) всегда будет возвращать 4. Вы хотите использовать strlen ().

Редактировать: IIRC, sizeof оценивается во время компиляции, он заботится только о типе, а не о содержимом.

1 голос
/ 18 декабря 2008

Это потому, что myArray - это указатель, который занимает 4 байта. Если вы хотите получить длину вашей строки, используйте strlen или что-то подобное.

0 голосов
/ 25 ноября 2014

хорошо, если бы вы собирались использовать sizeof (myArray), вы должны были сделать sizeof (* myArray); потому что с указателями, ни одна звезда не является адресом, а не значением. Как это:

char *myArray;
cin >> *myArray;
cout << *myArray;
0 голосов
/ 18 декабря 2008

Как уже говорили другие sizeof возвращает размер объекта, переданного ему, в случае указателя это размер указателя. sizeof не не следует за указателем, чтобы увидеть, на какой размер указывает объект, на который он указывает (как он может знать, что он может указывать на один char или на массив, который не очень хорошо знать) 1006 *

Кроме того, когда вы читаете из cin, вам нужно выделить некоторое пространство, в которое должны быть прочитаны данные, cin не выделит вам место. Вы можете выделить место либо в стеке, либо в куче:

char stack_line[1024]; // This will overflow if more than 1024 chars are needed
char heap_line*  = new char[1024]; // ditto

Здесь следует отметить, что sizeof(stack_line) == 1024 while sizeof(heap_line) == 4 [на 32-битных машинах] , поэтому вы должны быть осторожны при использовании оператора sizeof.

На практике лучше использовать std::string, который знает, как распределить само пространство.

0 голосов
/ 18 декабря 2008

Как уже говорили, myArray - это указатель.

Но почему бы вам не использовать std::string? Вам не нужно делать выделение буфера самостоятельно, что вы делаете неправильно в вашем примере (указатель myArray указывает на ничто)

std::string myValue;
std::cin >> myValue;
std::cout << myValue.length();

При необходимости вы можете получить указатель на представление строки, используя string::c_str().

0 голосов
/ 18 декабря 2008

Это потому, что вы используете sizeof () для указателя, который составляет 4 байта на вашем 32-битном компьютере:

printf("Pointer size: %d\n", sizeof(void*));

Если ваш массив является строкой с нулевым символом в конце (последний элемент является нулевым байтом или '\ 0'), тогда вы можете использовать

strlen(myArray)

чтобы получить количество элементов (минус один). E.g.:

myArray = "Hello, world!";
printf("Number of characters: %d\n", strlen(myArray));

Вы также можете использовать статически размещенный массив, например:

 char array[128];
 printf("sizeof(array) = %d\n", sizeof(array));
 // prints 128
0 голосов
/ 18 декабря 2008

Кажется, у вас здесь много проблем:

myArray не инициализирован - где будет жить ввод?

Вы обычно используете: cin >> myArray; (Обратите внимание на направление шевронов и точки с запятой)

sizeof (myArray) всегда будет возвращать одно и то же значение (4 на вашей платформе)

Попробуйте эту версию вместо:

char* myArray= new char[50];
cin >> myArray;
cout << myArray;
cout << strlen(myArray);

Не без его собственных проблем (я должен был удалить myArray), поэтому вы должны попробовать ответы здесь, которые используют string myArray

...