制作一个令牌数组并将其与另一个字符串进行比较

时间:2013-12-06 19:36:28

标签: c

我有一个来自控制台的*输入字符串。该字符串可能如下所示:show name year xxx ..我需要一个输出看起来像这样: 姓名:阿迪 年:1994年(例如)..

我一直试图通过使用strtok()函数来实现这一点,但我还需要将每个tokon与允许的关键词(name,year ...)进行比较,如果不允许这个词,那么令牌需要被滑雪(删除)..例如在这种情况下它会跳过show和xxx。

另一个问题是我需要以数组形式使用这些令牌才能使用它们并使用结构。 可以在输入中输入的单词数量没有限制..

我希望你理解我的问题..所以,如何使用strtok或其他东西从字符串中创建标记,使它们成为数组或指针,以及如何将这些标记与另一个字符串进行比较(例如常量:#define NAME“name”)以及其他一些输入可以跳过(删除)它们。

如果你能帮助我,我真的很感激..谢谢......

2 个答案:

答案 0 :(得分:0)

我会避免使用数组。它提供了不必要的开销你要求的东西可以用这样的东西来完成:

void parseString(char * string) {
    char * name = NULL;
    char * year = NULL:
    char * ptr = strtok(string, " ");
    while (ptr != NULL) {
        if (stricmp(ptr, "name") == 0) {
            ptr = strtok(ptr, " ");
            name = ptr;
            /* do whatever with name */
        } else if (stricmp(ptr, "year") == 0) {
            ptr = strtok(ptr, " ");
            /* do whatever with year */
            year = ptr;
        } /* else if ... */

        ptr = strtok(ptr, " ");
    }

这为您提供了相当大的灵活性。您可以检查所需的所有术语,无需担心如何分配阵列,并且可以在必要时访问设置值。

答案 1 :(得分:0)

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#include <stdbool.h>

char *tolowerstr(char *str){
    char *p = str;
    while((*p++ = tolower(*p)));
    return str;
}

int cmp(const void *a, const void *b){
    return strcmp(*(const char **)a, *(const char **)b);
}

bool isBanWord(const char *word){
    static const char *table[] =
        { "fuck", "show", "xxx" };//sorted
    char **ret, *key;
    key = tolowerstr(strdup(word));
    ret=bsearch(&key, table, sizeof(table)/sizeof(*table), sizeof(*table), cmp);
    free(key);

    return !!ret;//ret != NULL ? true : false;
}

//Create and return as a dynamic array of pointer to the copy of the word from a string.
//String passed is destroyed.
char **strToWords(char *str, size_t *size){
    const char *delimiters = " .";
    size_t count=0;
    char **array = malloc(strlen(str)*sizeof(char*));//number of words < string length
    if(array){
        char *token=strtok(str, delimiters);
        for(; token ;token=strtok(NULL, delimiters)){
            if(!isBanWord(token))//skip ban word
                array[count++] = strdup(token);
        }
        array[count] = NULL;//End mark
        array=realloc(array, (count + 1)*sizeof(*array));//include NULL
    }
    *size = count;
    return array;
}

typedef struct words {
    char **words;
    size_t n; //number of words
} Words;

void clearWords(Words *w){
    size_t i;
    for(i=0;i < w->n;++i)
        free(w->words[i]);
    free(w->words);
    w->words = NULL;
    w->n = 0;
}

void printWords(Words *w){
    size_t i=0;
    while(i < w->n){
        printf("%s", w->words[i++]);
        if(w->words[i])
            putchar(' ');
    }
    putchar('\n');
}

int main(){//DEMO
    char sentence[] = "show name year xxx.";//input string. Will be destroyed.
    Words w;

    w.words = strToWords(sentence, &w.n);

    printWords(&w);//name year

    clearWords(&w);

    return 0;
}