Проблема с регулярным выражением - PullRequest
2 голосов
/ 17 января 2011

У меня есть файл perl, который принимает txt-файлы и сравнивает их с другими словами в другом txt-файле, если они совпадают, тогда файл перемещается в другую папку

В настоящее время я получаю эту ошибку:

Unmatched ( in regex; marked by <-- HERE in m/\b( <-- HERE who\b/ at filter.pl line 45.

Моя строка 45 файла perl:

if ($x =~ m/\b$word\b/) {

Я не знаю, имеет ли это какое-либо отношение к остальной части файла, но я добавлю свой код просто в случае !! !! 1009 *

$dirtoget="/Users/jennie/crimes/";
opendir(IMD, $dirtoget) || die("Cannot open directory");
@thefiles= readdir(IMD);

foreach $f (@thefiles){
    if ($f =~ m/.txt/){
    #print "matches a txt file\n";
#print $f;
        open (FILE, "/Users/jennie/crimes/$f")or die"Cannot open FILE";

        if ( FILE eq "" ) {

            close FILE;
        }
        else{
       # print "In the Else\n";
            while (<FILE>) {
                foreach $word(split) {
                    foreach $x (@triggers) {
                        if ($x =~ m/\b$word\b/) {

                            print $word,"\n";
                                print $f,"\n";

                            copy("/Users/jennie/crimes/$f","/Users/jennie/crimeStories/$f")or die "Copy failed: $!";
                    close FILE;
                    } 
                    }

                }
            }
        }
    }
}
closedir(IMD);
exit 0;

Ошибка не имеет для меня большого смысла. Я далек от прихоти в регулярных выражениях: - (

Ответы [ 2 ]

3 голосов
/ 17 января 2011

Вы интерполируете содержимое $word непосредственно в регулярное выражение. Это означает, что любые метасимволы в $word будут интерпретироваться как метасимволы, потенциально нарушающие ваше регулярное выражение.

Если вы хотите сопоставить буквальное содержимое $word, используйте \Q и \E:

$x =~ m/\b\Q$word\E\b/

Кроме того, как @goreSplatter упомянул в комментариях, у вас есть еще одно сломанное регулярное выражение далее по странице:

$f =~ /.txt/

Прежде всего, . - это метасимвол, который соответствует любому символу . Во-вторых, он не привязан - регулярное выражение выполнится успешно, если эта последовательность символов появится в любом месте имени файла. Так, например, будет соответствовать "thisisnotatxtfile.bin".

Вы можете использовать модуль File :: Basename , чтобы извлечь просто расширение файла и проверить его, или вы можете изменить регулярное выражение, экранируя . и привязывая его к конец имени файла:

$f =~ /\.txt$/
1 голос
/ 17 января 2011

Это, вероятно, происходит потому, что $word содержит метасимвол.A ( в этом случае, который обозначает начало группы захвата.Это означает, что ваше регулярное выражение будет разбито, поскольку $word может содержать метасимволы.Вы можете использовать \Q и \E, чтобы убедиться, что содержимое $word "заключено в кавычки", поэтому оно не будет интерпретироваться как метасимволы:

$ x = ~ m / \b \ Q $ word \ E \ b /

Более подробная информация здесь .

РЕДАКТИРОВАТЬ

Исходя из комментария tchrist, \b не будет иметь смысла в этом контексте, если вы не убедитесь, что $word содержит только буквенно-цифровые символы.Но в целом, чтобы обойти вашу проблему, используйте:

$x = m/\Q$word\E/
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...