LINUX.ORG.RU

Проблемы с массивами строк


0

0

Стоит простая задача - считать со стандартного ввода строки в массив. Соответственно об'являю char **arrWord, однако в этом случае рано или поздно валится сегментация. Можно обойти путем об'явления char *arrWord[int _value], но это не есть хорошо. Как это можно обойти ?

anonymous

char **arrWord;

arrWord = (char**)malloc(sizeof(char**) * <kol-vo strok>); /* XXX */ free(arrWord);

lg ★★
()

sizeof(char**) заменить на sizeof(char*) :)

lg ★★
()

Очень часто встречающийся алгоритм!

lg (*) (2002-08-23 16:13:18.416):
malloc(sizeof(char**) * <kol-vo strok>)
и есть то, что по условиям задачи "не есть хорошо"

Я обычно примерно так делаю:

char **text = NULL;
unsigned int top_text=0;
unsigned int max_top_text = 0;
char buf[MAX_STRLEN];

...
if(fgets(buf,MAX_STRLEN,stdin)!=NULL){
   if(top_text>=max_top_text)
      if(
           (text=realloc(text,
              (max_top_text+=DELTA_TEXT)*sizeof(char *))
           )==NULL
        ){обработка исключения}
   text[top_text++]=strcpy(buf,(char*)getmem((size_t)(strlen(buf)+1),1));
}
...
text=realloc(text,top_text); max_top_text=top_text;
...

где getmem - следующий wrapper к calloc'у:

void *getmem(size_t nitems, size_t size)
{
    void *tmp;
   if( ((tmp=calloc(nitems,size))==NULL)&&(nitems!=0) )
     {обработка исключения} 
   return(tmp);
}

Если DELTA_TEXT поставить в 1, то строка 
text=realloc(text,top_text); max_top_text=top_text;
лишняя, при этом на огромных массивах потеряешь пару секунд.
Я обычно ставлю 
#define DELTA_TEXT <ожидаемое кол-во строк + 20%>
хотя это и пижонство.

Die-Hard ★★★★★
()

Гм... а может, анонимуса спасёт vector<string> ss?

string s;
ifstream ist("file.txt");
while ( ist )
{
    getline(ist, s);
    ss.push_back(s);
}

hbee ★★★★
()

В условиях было со стандартного ввода, sorry :)

hbee ★★★★
()

hbee (*) (2002-08-23 18:20:05.955):
> Гм... а может, анонимуса спасёт vector<string> ss?
Ну, на ЦеПП, конечно, дядя все давно за тебя сделал ;)

hbee (*) (2002-08-23 18:22:22.123):
> В условиях было со стандартного ввода, sorry :)
В ЧЕМ ПРОБЛЕМА?

#include <iostream>
#include <string>
#include <vector>

int main(void)
{
string s;
vector<string> ss;
   while (!cin.eof()){
     ...
    cin >>s;
    if (!cin.eof()) ss.push_back(s);
     ...
   }
}

Die-Hard ★★★★★
()

>> Гм... а может, анонимуса спасёт vector<string> ss? >Ну, на ЦеПП, конечно, дядя все давно за тебя сделал ;)

И это хорошо :))) Я - карлик, стоящий на плечах гигантов :)))

hbee ★★★★
()
Ответ на: комментарий от hbee

hbee (*) (2002-08-23 19:05:47.895):
> Я - карлик, стоящий на плечах гигантов :)))
Хреновато стоишь, если не умеешь с cin'а строку ввести :)


Die-Hard ★★★★★
()

Блин, да умею я, просто посчитал, что идея ясна из уже приведённого фрагмента.

Кстати, if ( !сin.eof() ) можно смело заменить на if ( cin )

Гораздо душевнее получается :)))

hbee ★★★★
()
Ответ на: комментарий от Die-Hard

Кстати, в Вашем примере был имплементировано заполнение вектора 
_словами_, а не строками:) 

BTW, заполнение _словами_ можно имплементировать еще проще (хотя, 
простота - понятие относительное ... ) 

//-----------------------------------
#include <string> 
#include <vector> 
#include <iostream> 
#include <iterator> 
#include <algorithm>

using namespace std ; 
void 
foo() { 
    vector<string> v ; 
    // заполняем вектор 
    copy( istream_iterator<string>(cin),istream_iterator<string>(),back_insert
er(v)); 
    // печатаем заполненый вектор 
    copy( v.begin(),v.end(),ostream_iterator<string>(cout,", ")); 
}
//-----------------------------------

omerm
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.