Применение strstr() несколько раз в одной строке в C

Я пытаюсь написать код, который извлекает все слова / строки между тегами и, используя strstr. Но кажется, что он просто застревает в первой извлеченной строке, которая является "быстрой". Как я могу получить код для продолжения после извлечения первой строки?

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

int main()
{

    char feed[] = "The <item> quick </item> brown <item> fox </item> jumps <item> over </item> the <item> lazy dog </item>";


    const char needle[] = "<item>";
    const char popo[] = "</item>";
    char *ret;
    char *ter;
    int n;
    n = 0;

    while (feed[n] != '\0')
    {
        ret = strstr(feed, needle)+6;
        ter = strstr(ret, popo);
        size_t len = ter - ret;
        char *res = (char*)malloc(sizeof(char)*(len+1));
        strncpy(res, ret, len);
        res[len] = '\0';

        printf("%s",res);
        n++;
    }
    return 0;
}

2 ответа

Решение

Вам нужно сделать ret указатель, указывающий на текущую позицию в строке, увеличивающий ее по длине на каждой итерации и передающий ret к первому strstr() вместо feed, проверьте эту реализацию

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

int main()
{

    char       feed[]   = "The <item> quick </item> brown <item> fox </item> "
                          "jumps <item> over </item> the <item> lazy dog </item>";
    const char needle[] = "<item>";
    const char popo[]   = "</item>";
    char      *head;
    int n;
    n = 0;

    head = feed;
    while (feed[n] != '\0')
    {
        char  *tail;
        char  *copy;
        size_t length;

        head = strstr(head, needle);
        /*            ^ always start at the current position. */
        if (head == NULL)
         {
            fprintf(stderr, "Invalid input...???\n");
            return -1;
         }
        tail   = strstr(head, popo);
        length = tail - head - 6;
        head  += 6;
        if (length < 0)
         {
            fprintf(stderr, "Invalid input...???\n");
            return -1;
         }
        copy = malloc(length + 1);
        if (copy != NULL)
         {
            memcpy(copy, head, length);
            copy[length] = '\0';

            printf("*%s*\n", copy);
            /* If you are not going to keep it, free it */
            free(copy);
         }
        head += length; /* <-- this is the imprtant thing */
        n++;
    }
    return 0;
}

На этой линии:

ret = strstr(feed, needle)+6;

Вы всегда начинаете свой поиск с начала feed строка. Вам нужно пройти другую отправную точку strstr, который у вас уже есть в ter, Таким образом, вы должны быть в состоянии сделать что-то вроде этого:

ter = feed;
while (ter != NULL) 
{
     ret = strstr(ter, needle) + 6;
...

При этом начало поиска будет продолжать двигаться вниз по feed строка.

В вашем коде есть другие проблемы:

  1. strstr() может вернуть NULL, если совпадение не найдено - вам нужно проверить это, или ваша программа потерпит крах.
  2. Вам нужно free() память, которую вы malloc()
  3. Как @iharob указывает: " Не бросайтеmalloc()"
Другие вопросы по тегам