Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > C/C++: Для новичков > работа с набором слов


Автор: FreeJaile 29.2.2008, 17:42
Здраствуйте. Мне нужно задать набор слов, построить любую цепочку из них так, чтобы последняя буква одного слова совпадала с первой буквой последующего(этого ещё не делала, поэтому функцию cheking просто как пример работы с этим массивом поместила). Задаю массив. И как я поняла из всего прочитанного, работать с этим массивом я могу только через указатель... но что-то запуталась( 

вот в этой строчке :  "if (strncmp (p[i], p[i+1], 1) == 0)"  выдает ошибку 'strncmp' : cannot convert parameter 1 from 'char' to 'const char *'

Код

const int n = 3;
void cheking (char *p);

void main(){

    //----------------------------------------------------------массив
    char *word[] = {"one", "two", "three"};

    char* p = new char[15];
         for (int i=0; i<n; i++) strcpy(p, word[i]); 

    for (i=0; i<n; i++) printf (" word [%d] = %s\n", i+1, word[i]);

    cheking (p);
    //-----------------------------------------------------------------
}

void cheking (char *p){
    for (int i=0; i<n; i++) {
         if (strncmp (p[i], p[i+1], 1) == 0) {
            printf ("\np[i] = %s p[i+1] = %s\n", p[i], p[i+1]);
            break;
        }
    }
}

Автор: Christoph 29.2.2008, 22:09
Ошибка пишет то что нельзя конвертировать параметры, мне кажется ты при описании функции указала char* p тоесть будет передавать не массив а одна строка!

Автор: FreeJaile 29.2.2008, 22:58
Цитата(Christoph @ 29.2.2008,  22:09)
Ошибка пишет то что нельзя конвертировать параметры, мне кажется ты при описании функции указала char* p тоесть будет передавать не массив а одна строка!

да..точно (я проверяла криво, в цикл вывод р записала)

но так и не поняла как передать массив в функцию =( подскажите, плз

Автор: prof_GCC 1.3.2008, 09:31
Цитата

да..точно (я проверяла криво, в цикл вывод р записала)

но так и не поняла как передать массив в функцию =( подскажите, плз

Все предельно просто, массивы в функции передаются через указатели, поэтому, если у тебя строка, то она указывает на массив символов, т.е. в функцию ты передаешь либо char**, поэтому в функцию сравнения можно смело передовать твою переменную word как только прототип функции станет checking(char**). Крогме того strncmp (p[i], p[i+1], 1) == 0 не соответствует тому, что тебе нужно, ты сравниваешь первые символы строки smile

Автор: MAKCim 1.3.2008, 10:13
Цитата(prof_GCC @  1.3.2008,  09:31 Найти цитируемый пост)
Крогме того strncmp (p[i], p[i+1], 1) == 0 не соответствует тому, что тебе нужно, ты сравниваешь первые символы строки

вообще говоря, здесь должна быть ошибка Access Violation/Segmentation Fault
т. к char (1 байт) знаково преобразуется к указателю (4 байта или 8 байт)

Автор: prof_GCC 1.3.2008, 10:28
Нет, я имел ввиду после изменения прототипа на checking(char**) и передачи в функцию переменной word

Автор: FreeJaile 19.3.2008, 17:46
мне нужно эту задачу оказывается списком делать((

как в списке сравнить последнюю букву рассматриваемого слова с первой буквой следующего?

использую структуру 

Код

struct words{
    char word[30];
    words* next;
};



подсчитываю длину слова так:


Код

void chain(words* beg){
    int lenth;
    words* curent_p = beg;
    while (curent_p){
        lenth = 0;
        lenth = strlen (curent_p -> word);
        //printf ("\n %d \n", lenth);
        curent_p = curent_p -> next;
    }
    
}


просьба модераторам переименовать тему в..например просто "набор слов" (ну или на усмотрение модератора соответственно)

Автор: klaq 28.3.2008, 15:19
Есть вопрос, коль уж тема по работе с набором слов.
Взаимодействие клиент-сервер по протоколу UDP, клиент посылает на сервер набор слов, тот возвращает количество одинаковых слов. С клиентами и серверами разобрался, а вот со словами похуже, вроде как понимаю, что надо было-бы строку расчленить на слова, их записать в массив и поискать, но вот с реализацией пока никак, подсобите, плиз!

Автор: Rififi 28.3.2008, 20:42
Цитата(klaq @  28.3.2008,  15:19 Найти цитируемый пост)
строку расчленить на слова,

в простейшем случае - функция из стандартной си-библиотеки strtok (есть свои особенности, например strtok не является потоко-безопасной)

или можно boost заюзать:

Код

#include <string>
#include <vector>
#include <boost/algorithm/string/classification.hpp>
#include <boost/algorithm/string/split.hpp>

    std::string s = "...";
    std::vector<std::string> res;

    boost::split(res, s, boost::is_any_of("список_разделитклей"));

Автор: klaq 29.3.2008, 12:00
Я сделал немного по-другому (входная строка - z) порезал ее на слова и забил их в массив:
Код

while((sscanf(z+=n," %s%n",y[i], &n))>0) i++;


В Си я пока зеленейший новичок, так VB малость, да 1С, так что строго не судите. Теперь вот вторая проблема, как забить в массиве сравнение.
Я пошел простейшим путем)):
Код

for (m=0;m<i;m++)
        for (p=1;p<i;p++)
            if ((y[p]==y[m])&&(p!=m)) 

Но почему-то сравнение y[p]==y[m] не работает. В чем тут может быть дело?

Автор: MAKCim 29.3.2008, 12:30
klaq, 
strcmp()/strncmp()

Автор: MAKCim 29.3.2008, 13:00
Цитата(klaq @  28.3.2008,  15:19 Найти цитируемый пост)
что надо было-бы строку расчленить на слова, их записать в массив и поискать, но вот с реализацией пока никак, подсобите, плиз! 

я бы сделал так
Код

long offsets[MAX_STRINGS]; /* MAX_STRINGS - максимальное количество слов в строке */
...
/* str - входная строка */
char s, *ptr = str;
int flags = 0, index = 0, position, count;
for (; (s = *str++); ) {
    switch (s) {
        case '\n':
        case '\r':
        /* остальные разделители */
            *(str - 1) = '\0';
            flags = 1;
            break;
        default:
            if (!flags) continue;
            flags = 0;
            offsets[index++] = str - ptr - 1;
    }
}
while (--index >= 0) {
    if (offsets[index] == -1)
        continue;
    count = 1;
    for (position = index - 1; position >= 0; --position) {
        if (offsets[position] == -1)
            continue;
        if (!strcmp(ptr + offsets[position], ptr + offsets[index])) {
            offsets[position] = -1;
            ++count;
        }
    }
    /* count - содержит количество слов ptr + offsets[index] */
}

Автор: klaq 29.3.2008, 14:07
MAKCim, 
Большое спасибо! 
Мой вопрос - это задание из обычной лабы по "Комп. сетям" и я без лишних мудрствований сделал через массив  и strcmp, жестко ограничив длину строки и размер массива. Для жизни, конечно, непригодно  smile , но для зачета сойдет.

Автор: FreeJaile 2.4.2008, 19:22
Код

#include <stdio.h>
#include <string.h>

int main(char **array, int n);
void chain(char **array, int n);
char **array;

int main(char **array, int n){
    printf ("\nHow many words you'll enter:\n");
    scanf ("%d", &n);
    if (n == 0) {
        printf ("\nError: wrong value\n");
        return 1; 
    }

    array = new char *[n];
    if (array == 0){
         printf ("\nError: array haven't been done\n");
         delete []array;
         return 1;
     }
 
    printf ("\nArray created succsesfully\nPlease, enter words:\n");

    printf ("\nPlease, enter %d words\n", n);
    for (int i = 0; i<n; i++){
        printf("\n%d: ", i+1); 
        scanf (" %s", &array[i]);
    }
    printf ("\nYou've entered the following array:\n");
    for (i = 0; i<n; i++) printf ("%s ", array[i]);

    chain (array, n);

    delete [] array;
    return 0;
}


void chain(char **array, int n){
    int k=0;
    for (int i=0; i<n; i++){
        if (k<n){
            if (array[k][strlen(array[k])-1] == array[i][0]){
                printf ("%s %s", array[k], array[i]);
                k=i;
                chain(array, n);
            }
        }
    }

    if (k==n){
        if (array[i][strlen(array[i])-1] == array[k][0]) printf (" %s %s",array[i], array[k]);
    }
}


вот на этом месте вылетает на выполнении (т.е. не выводит массив)
Код

    printf ("\nYou've entered the following array:\n");
    for (i = 0; i<n; i++) printf ("%s ", array[i]);


подскажите, плз, в чем ошибка...

Автор: Dmi3ev 2.4.2008, 19:48
на первый взгляд
Код

printf ("\nYou've entered the following array:\n");
    for (int i = 0; i<n; i++) printf ("%s ", array[i]);


Автор: FreeJaile 2.4.2008, 20:11
во-первых, тогда бы вообще не запустилось ничего на выполнение.
во-вторых, там в той же ф-ции раньше объявляется i
(:

Автор: Dmi3ev 2.4.2008, 20:16
ну по идее, если ты объявляешь i в цикле, то после завершения цикла нет никакого i, поэтому и сказал smile  

Автор: FreeJaile 3.4.2008, 21:49
Вопрос все ещё в силе. Если у кого-то есть ещё какие-либо идеи, не молчите пожалст (:
на мой взгляд там нет ошибок по крайней мере до этого места, которое я указала %) может, с распределением памяти там что-то не так?

Автор: Dmi3ev 3.4.2008, 21:56
есть набор слов (как он задается, программно или с клавы?), допустим собака, арбуз, заяц, надо вывести цепочку. я так понимаю, ответом будет собака заяц арбуз. а если нет таких слов, которые удовлетворяют условию? вообщем напиши поподробнее, что должно получиться smile 

Автор: FreeJaile 3.4.2008, 22:16
набор слов задается с клавы и сколько хочет пользователь, поэтому и завела динамич. массив))
прога должна выводить любую(можно в принципе и одну, но тогда максимальной длины) цепочку слов т.е. 
собака заяц арбуз -> собака арбуз.
заяц солнце арбуз собака -> собака арбуз.

но там по заданию старый вариант с ошибками (в функции chain)  smile 
но вот почему же вылетает на выполнении..

Автор: Dmi3ev 3.4.2008, 22:39
Цитата

заяц солнце арбуз собака -> собака арбуз.

а почему не собака арбуз заяц (ведь заяц на з начинается а арбуз на з заканчивается)?

Автор: FreeJaile 3.4.2008, 22:41
:упс: я просто не заметила.)

Автор: Dmi3ev 3.4.2008, 22:57
вот теперь я догнал суть)))

Добавлено через 1 минуту и 58 секунд
надо подумать)))

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)