Сопоставление границ слов не работает в C

Я пытаюсь выяснить, существует ли в предложении полное слово, скажем test, и мне хотелось бы сделать это без учета регистра. Я воспользовался возможностями регулярных выражений в C и использовал \b в шаблоне. Вот программа

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

int main() {
    const char* hay = "This Is a TEst, or not!";

    regex_t regex;
    if (regcomp(&regex, "\btest\b", REG_EXTENDED | REG_ICASE)) {
        printf("compilation failed\n");
    }

    regmatch_t match[1];
    if (regexec(&regex, hay, 1, match, 0) == REG_NOMATCH) {
        printf("couldn't match\n");
    }
}

Когда я запускаю эту программу, она печатает couldn't match, но предложение явно содержит слово TEst. Может ли кто-нибудь указать на проблему?

Кажется, вам нужно написать "\\btest\\b"

Vlad from Moscow 28.06.2024 17:24
\b — символ возврата. Возможно, какая бы библиотека, которую вы используете (PCRE?), требует фактической обратной косой черты и символа b, так что \\b?
Paul Hankin 28.06.2024 17:25

Даже при правильном экранировании расширенные регулярные выражения posix не имеют утверждений о границах слов.

Shawn 28.06.2024 17:32

И пока вы проверяете, не удалось ли regcomp(), все, что вам нужно сделать, это распечатать сообщение, а затем продолжить работу, как будто оно удалось. Это не обернется хорошо.

Shawn 28.06.2024 17:35

Вам нужно использовать библиотеку PCRE, чтобы получить escape-последовательность \b для границ слов. pcre.org

Barmar 28.06.2024 19:06
Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
2
5
73
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

Есть две проблемы. \b — символ пробела. Даже если вы исправите это, удвоив обратную косую черту \\b, regcomp не распознает это как шаблон и будет искать обратную косую черту, за которой следует символ b.

Чтобы это работало, вам необходимо настроить регулярное выражение в соответствии с возможностями механизма регулярных выражений (см. страницу руководства regex(7)).

Измените свое регулярное выражение на: "[^[:alnum:]]test[^[:alnum:]]", и вы добьетесь большего успеха.

Обновление. Обратите внимание, что это регулярное выражение также вернет граничные символы. Если вам нужно сохранить проверяемое слово, используйте "[^[:alnum:]](test)[^[:alnum:]]" и соответствующим образом настройте массив match[], чтобы получить совпадающие данные.

Обновление 2: Как отметил @barmar, это не будет работать для текста в начале или конце строки. Чтобы справиться с этим, регулярное выражение необходимо изменить на "(^|[^[:alnum:])(test)([^[:alnum:]]|$)".

Это не будет соответствовать слову в начале или конце строки.

Barmar 28.06.2024 19:05

Другие вопросы по теме