Модераторы: Daevaorn

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Не получается создать массив по размеру другого... 
:(
    Опции темы
Вп
Дата 16.8.2005, 10:43 (ссылка)    |    (голосов: 0) Загрузка ... Загрузка ... Быстрая цитата Цитата


Unregistered











Доброе время суток. Возникла проблема. Мне необходимо (в учебных целях) написать функцию, которая бы получала в качестве аргументов строку (char-массив), и переворачивала ее.
Попробовал вот так:
Код

void rev(char s[])
{
    char ch='\0';
    //const int i=strlen(s)+1;    //не работает!
    const int i=sizeof(s);
    char s2[i];
    for (int count1=i, count2=0; count1>=0; count1--, count2++)
//дальше пока неинтересно….
}

Столкнулся с трудностями уже на момент инициализации переменных. Как видно из примера, я хотел создать временный массив s2, равный по размеру массиву-аргументу s, и посимвольно скопировать в него в обратном порядке содержимое массива-аргумента.
Проблема в том, что компилятор ругается, если я пытаюсь определить размер временного массива через закоментированную строчку, а sizeof (s) возвращает неправильный результат: например, если передается строка "as458", sizeof(s) возвращает результат 4, хотя, если я все правильно понимаю, каждый char-элемент массива занимает один байт, следовательно, размер массива должен быть шесть байт (включая завершающий нуль-символ).


  Вверх
chaos
Дата 16.8.2005, 10:55 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Серийный программист
****


Профиль
Группа: Завсегдатай
Сообщений: 2979
Регистрация: 7.7.2004
Где: Екатеринбург

Репутация: 6
Всего: 44



делай не sizeof а strlen
PM WWW   Вверх
Hroft
Дата 16.8.2005, 10:57 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 310
Регистрация: 20.10.2003
Где: Москва

Репутация: нет
Всего: 3



Все правильно сайзоф тебе говорит. 4 - это размер указателя на char, коим является твой формальный аргумент. Тебе придется либо использовать класс std::string, либо передавать также и размер в еще одном аргументе. Ну или самому определять размер, пробегаясь от первого символа, указатель на который есть, до символа конца строки. Но это не самый лучший вариант, по-моему.
Именно это и делает strlen, наверняка, про которую я забыл, а chaos напомнил.

Это сообщение отредактировал(а) Hroft - 16.8.2005, 10:58
PM MAIL ICQ   Вверх
Вп
Дата 16.8.2005, 11:00 (ссылка)    |    (голосов: 0) Загрузка ... Загрузка ... Быстрая цитата Цитата


Unregistered











Спасибо, разобрался! ФУнкция с 2-мя аргуменами - мой выбор smile)
Но все же, strlen дает правильный результат, но почему такой результат не получается вставить в обявление массива???
  Вверх
chaos
Дата 16.8.2005, 11:02 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Серийный программист
****


Профиль
Группа: Завсегдатай
Сообщений: 2979
Регистрация: 7.7.2004
Где: Екатеринбург

Репутация: 6
Всего: 44



Цитата
Но все же, strlen дает правильный результат, но почему такой результат не получается вставить в обявление массива???

потомучто ты наверное его создаешь как-нибудь так
char mas[strlen(mas2)];
а надо
char *mas = new char[strlen(mas2)+1];
...
delete[] mas


одним словом так нельзя создавать массивы! Размер массива в статической памяти должен быть известен на этапе компиляции

Это сообщение отредактировал(а) chaos - 16.8.2005, 11:12
PM WWW   Вверх
Mayk
Дата 16.8.2005, 11:02 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


^аВаТаР^ сообщение>>
****


Профиль
Группа: Участник
Сообщений: 2616
Регистрация: 22.5.2005
Где: за границей разум а

Репутация: 45
Всего: 134



Цитата
void rev(char s[])
{
    char ch='\0';
    //const int i=strlen(s)-1;
    const int i=sizeof(s);
    char s2[i];
    for (int count1=i, count2=0; count1>=0; count1--, count2++)
//дальше пока неинтересно….
}

strlen(s)+1 вообще не принадлежит строке - бо это байт, следующий за 0, означающим конец строки.


--------------------
 Здесь был кролик. Но его убили.
Человеки < кроликов, йа считаю.
PM MAIL WWW ICQ   Вверх
Вп
Дата 16.8.2005, 11:19 (ссылка)    |    (голосов: 0) Загрузка ... Загрузка ... Быстрая цитата Цитата


Unregistered











Что-то обрадовался, а похоже рано...
Попытка вызова функции с 2-мя параметрами дает тот-же самый косяк, что и при попытке определить размер массива s2 через strlen:
Вот полный пример кода, который я пытался откомпилировать:
Код

#include <iostream>
using namespace std;


void mstold(char s[], int i2)
{
    char s2[i2];
}


void main()
{    

}


А вот сообщения компилятора:
C:\PROECT\LIPMAN\007\007.cpp(7) : error C2057: expected constant expression
C:\PROECT\LIPMAN\007\007.cpp(7) : error C2466: cannot allocate an array of constant size 0
C:\PROECT\LIPMAN\007\007.cpp(7) : error C2133: 's2' : unknown size
Error executing cl.exe.

Ругается на строку char s2[i2], считает синтаксис неверным, хотя я ее даже вызвать не пытаюсь, просто пока описал функцию.
Может, глаз замылился, и я не вижу очевидной ошибки?
  Вверх
Вп
Дата 16.8.2005, 11:22 (ссылка)    |    (голосов: 0) Загрузка ... Загрузка ... Быстрая цитата Цитата


Unregistered











Так, пока писал, пришло два ответа smile), chaos, твой последний пример содержит указатель, а мне принципиально надо работать с простым char-массивом. Получается, решения для простого массива нет smile((
  Вверх
Hroft
Дата 16.8.2005, 11:23 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 310
Регистрация: 20.10.2003
Где: Москва

Репутация: нет
Всего: 3



Тебе уже все написали.
Ты должен объявлять не статический массив, а динамический, поскольку на этапе компиляции неизвестен размер. Почитай пост chaos'а.
PM MAIL ICQ   Вверх
chaos
Дата 16.8.2005, 11:25 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Серийный программист
****


Профиль
Группа: Завсегдатай
Сообщений: 2979
Регистрация: 7.7.2004
Где: Екатеринбург

Репутация: 6
Всего: 44



Цитата
Так, пока писал, пришло два ответа smile), chaos, твой последний пример содержит указатель, а мне принципиально надо работать с простым char-массивом. Получается, решения для простого массива нет smile((

не нравятся динамические массивы, делай заведомо БОЛЬШИЕ статические вот и все

типо:
#define MAXSTR 1024

Код

char mas[MAXSTR];
...


Это сообщение отредактировал(а) chaos - 16.8.2005, 11:26
PM WWW   Вверх
Hroft
Дата 16.8.2005, 11:25 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 310
Регистрация: 20.10.2003
Где: Москва

Репутация: нет
Всего: 3



Не понимаю, как это принципиально нужно работать со статическим массивом, но тогда используй массив размеров символов в 100, или сколько у тебя там максимум может понадобиться, и каждый раз оперируй только с его частью. Ты по задумке чтоли еще не можешь new пользовать?
PM MAIL ICQ   Вверх
Вп
Дата 16.8.2005, 11:26 (ссылка)    |    (голосов: 0) Загрузка ... Загрузка ... Быстрая цитата Цитата


Unregistered











Майк, если правильно понимаю, strlen возвращает размер строки в символах (то есть int число), а значит strlen()+1 - это всего лишь число символов строки+1...
  Вверх
chaos
Дата 16.8.2005, 11:27 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Серийный программист
****


Профиль
Группа: Завсегдатай
Сообщений: 2979
Регистрация: 7.7.2004
Где: Екатеринбург

Репутация: 6
Всего: 44



Цитата
Майк, если правильно понимаю, strlen возвращает размер строки в символах (то есть int число), а значит strlen()+1 - это всего лишь число символов строки+1...

strlen возвращает кол-во символов без \0
пример
Код

char s = "12345";
printf ("%d\n", strlen(s)); //выведет 5


те получается если тебе надо скопировать строку в строку s2 она должна иметь размер strlen(s) + 1, те 5 байт для 12345 и один для \0

Это сообщение отредактировал(а) chaos - 16.8.2005, 11:31
PM WWW   Вверх
Mayk
Дата 16.8.2005, 11:52 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


^аВаТаР^ сообщение>>
****


Профиль
Группа: Участник
Сообщений: 2616
Регистрация: 22.5.2005
Где: за границей разум а

Репутация: 45
Всего: 134



Ну вот. chaos за меня уже ответил smile
единственное, что могу добавить -
обрати внимание на условие:
for (int count1=i, count2=0; count1>=0; count1--, count2++)
если использовать иное, нежели i=strlen(s)-1, то с таким условием будут глюки - так s[i] возвратит нуль, и(надо полагать, хотя кода нет) этот нуль запишется в самое начало второй строки => вторая строка будет сильно обрезана.
Кстати, можешь заместо new посмотреть alloca (он присутствует в старом bc3.1), память выделенная через него освободится автоматически при выходе из ф-ции.


--------------------
 Здесь был кролик. Но его убили.
Человеки < кроликов, йа считаю.
PM MAIL WWW ICQ   Вверх
Denn
Дата 16.8.2005, 12:26 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 143
Регистрация: 6.8.2005

Репутация: нет
Всего: 2



STL используй. vector<> в данном случае.
PM MAIL ICQ   Вверх
Ответ в темуСоздание новой темы Создание опроса
Правила форума "С++:Общие вопросы"
Earnest Daevaorn

Добро пожаловать!

  • Черновик стандарта C++ (за октябрь 2005) можно скачать с этого сайта. Прямая ссылка на файл черновика(4.4мб).
  • Черновик стандарта C (за сентябрь 2005) можно скачать с этого сайта. Прямая ссылка на файл черновика (3.4мб).
  • Прежде чем задать вопрос, прочтите это и/или это!
  • Здесь хранится весь мировой запас ссылок на документы, связанные с C++ :)
  • Не брезгуйте пользоваться тегами [code=cpp][/code].
  • Пожалуйста, не просите написать за вас программы в этом разделе - для этого существует "Центр Помощи".
  • C++ FAQ

Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Earnest Daevaorn

 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Общие вопросы | Следующая тема »


 




[ Время генерации скрипта: 0.0695 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.