Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

что я не так делаю?

5 views
Skip to first unread message

Brother Rabbit

unread,
Jun 9, 2019, 7:00:02 AM6/9/19
to
Hi, All!

$words = 'по закону';

@wrds = split(" ", $words);
foreach $w ( @wrds ) {
$found = 0 if $text ~= /$w/i;
}

Находит "по новому закону", "попа закону", "гипопотам не указ закону". Цель же
найти тролько слово целиком.

@wrds = split(" ", $words);
foreach $w ( @wrds ) {
$found = 0 if $text ~= /\b$w\b/i;
}

не находит даже "по закону"

@wrds = split(" ", $words);
foreach $w ( @wrds ) {
$found = 0 if $text ~= /\b${w}\b/i;
}

тоже ни чего не находит.

Как правильно сделать?

Have nice nights.
Brother Rabbit.

Michael Dukelsky

unread,
Jun 9, 2019, 7:30:01 AM6/9/19
to
Привет, Brother!

09 June 2019 13:49, Brother Rabbit послал(а) письмо к All:

BR> $words = 'по закону';

BR> @wrds = split(" ", $words);
BR> foreach $w ( @wrds ) {
BR> $found = 0 if $text ~= /$w/i;
BR> }

BR> Находит "по новому закону", "попа закону", "гипопотам не указ закону".
BR> Цель же найти тролько слово целиком.

Не совсем понял, что ты хочешь.

#!/usr/bin/perl
my $words = "по закону";
my $text = "гипопотам закону не указ";
my @wrds = split(" ", $words);
my $found = 0;
foreach my $w ( @wrds )
{
print "w = $w\n";
if($text =~ /$w/i)
{
$found = 1;
last;
}
}
print "found = $found\n";

Находит "по" в слове "гипопотам". Это то, что ты хотел?

Желаю успехов, Brother!
За сим откланиваюсь, Michael.

... node (at) f1042 (dot) ru

Brother Rabbit

unread,
Jun 9, 2019, 9:35:01 AM6/9/19
to
Hi, Michael!

09 июн 19 14:18, Michael Dukelsky -> Brother Rabbit:

BR>> $words = 'по закону';

BR>> @wrds = split(" ", $words);
BR>> foreach $w ( @wrds ) {
BR>> $found = 0 if $text ~= /$w/i;
BR>> }

BR>> Находит "по новому закону", "попа закону", "гипопотам не указ закону".
BR>> Цель же найти тролько слово целиком.

MD> Не совсем понял, что ты хочешь.

MD> #!/usr/bin/perl
MD> my $words = "по закону";
MD> my $text = "гипопотам закону не указ";
MD> my @wrds = split(" ", $words);
MD> my $found = 0;
MD> foreach my $w ( @wrds )
MD> {
MD> print "w = $w\n";
MD> if($text =~ /$w/i)
MD> {
MD> $found = 1;
MD> last;
MD> }
MD> }
MD> print "found = $found\n";

MD> Находит "по" в слове "гипопотам". Это то, что ты хотел?

Наоборот. Я хотел, что бы находилось только "по", но не "гипопотам".

#!/usr/bin/perl

use locale;

[...skipped...]

if ( defined( $words ) ) {
$found = 1;
@wrds = split(" ", $words);
foreach $w ( @wrds ) {
$found = 0 if $msgtext !~ /[\.\, \t\r]${w}[\.\, \t\r]/i;
}
}

[...skipped...]

Вот так вылавливает слово целиком, но не слова, его содержащие. Однако, эта
конструкция [\.\, \t\r] не эквивалентна \b. Между тем, у меня острое ощущение,
что при таком использовании \b транслируется не в границу слова, а в символ
Back Space.

Michael Dukelsky

unread,
Jun 9, 2019, 12:50:01 PM6/9/19
to
Привет, Brother!

09 June 2019 16:11, Brother Rabbit послал(а) письмо к Michael Dukelsky:

MD>> Не совсем понял, что ты хочешь.

MD>> #!/usr/bin/perl
MD>> my $words = "по закону";
MD>> my $text = "гипопотам закону не указ";
MD>> my @wrds = split(" ", $words);
MD>> my $found = 0;
MD>> foreach my $w ( @wrds )
MD>> {
MD>> print "w = $w\n";
MD>> if($text =~ /$w/i)
MD>> {
MD>> $found = 1;
MD>> last;
MD>> }
MD>> }
MD>> print "found = $found\n";

MD>> Находит "по" в слове "гипопотам". Это то, что ты хотел?

BR> Наоборот. Я хотел, что бы находилось только "по", но не "гипопотам".

Тогда так:

#!/usr/bin/perl
my $words = "по закону";
my $text = "гипопотам закону не указ";
my @wrds = split(" ", $words);
my $found = 0;
foreach my $word ( @wrds )
{
print "word = $word\n";
if($text =~ /^$word\s/i)
{
$found = 1;
last;
}
if($text =~ /\s$word\s/i)
{
$found = 2;
last;
}
if($text =~ /\s$word$/i)
{
$found = 3;
last;
}
}
print "found = $found\n";

Eugene Grosbein

unread,
Jun 9, 2019, 4:40:01 PM6/9/19
to
09 июня 2019, воскресенье, в 13:49 NOVT, Brother Rabbit написал(а):

BR> $words = 'по закону';
BR> @wrds = split(" ", $words);
BR> foreach $w ( @wrds ) {
BR> $found = 0 if $text ~= /$w/i;
BR> }
BR> Hаходит "по новому закону", "попа закону", "гипопотам не указ закону".

Разумеется - тут нигде не сказано, что нужно искать слова целиком.

BR> Цель же найти тролько слово целиком.

BR> @wrds = split(" ", $words);
BR> foreach $w ( @wrds ) {
BR> $found = 0 if $text ~= /\b$w\b/i;
BR> }
BR> не находит даже "по закону"

Hет, находит - если исправить ошибки (=~ вместо ~=)
и вообще писать аккуратно. И почитать perldoc perlre.

#!/usr/local/bin/perl

use 5.22.0;
use strict;
use warnings;
use locale;

my @wrds = qw(по закону);
my $w;
foreach $w ( @wrds ) {
print "Hайдено: $w\n" if $ARGV[0] =~ /\b$w\b/i;
}

$ ./find.pl "по новому закону"
Hайдено: по
Hайдено: закону
$ ./find.pl "гипопотам не указ закону"
Hайдено: закону
$ ./find.pl "по закону"
Hайдено: по
Hайдено: закону


\b обозначает границу слова в регулярных выражениях.
backspace оно обозначает внутри классов символов (в квадратных скобках)
и вне регулярных выражений при интерполяции строк.

Eugene
--
Кара за одно съеденное яблоко, все-таки, была несоизмеримо велика,
приступ диареи послужил бы достаточным уроком.

Brother Rabbit

unread,
Jun 10, 2019, 2:05:02 AM6/10/19
to
Hi, Eugene!

10 июн 19 03:27, Eugene Grosbein -> Brother Rabbit:

BR>> Цель же найти тролько слово целиком.

BR>> @wrds = split(" ", $words);
BR>> foreach $w ( @wrds ) {
BR>> $found = 0 if $text ~= /\b$w\b/i;
BR>> }
BR>> не находит даже "по закону"

EG> Hет, находит - если исправить ошибки (=~ вместо ~=)

Опечатка в тексте письма. В коде правильно.

EG> и вообще писать аккуратно. И почитать perldoc perlre.

Там сказано, что \b{} для юникода работает начиная с версии 5.22.

EG> #!/usr/local/bin/perl

EG> use 5.22.0;

\b тоже только с 5.22 работает? В любом случае, в перлхуке HPT не получается
использовать use 5.22.0;, т.к. ругается на необявление всех переменных, в т.ч.
и вшитых в HPT перлхук.

[...skipped...]

EG> \b обозначает границу слова в регулярных выражениях.
EG> backspace оно обозначает внутри классов символов (в квадратных скобках)
EG> и вне регулярных выражений при интерполяции строк.

Вот, а еще сказано, что m// обрабатывается так же, как строка в двойных
кавычках и там возможа подстановка переменных. Это меня и смутило.

Eugene Grosbein

unread,
Jun 10, 2019, 5:55:01 AM6/10/19
to
10 июня 2019, понедельник, в 08:39 NOVT, Brother Rabbit написал(а):

BR>>> Цель же найти тролько слово целиком.
BR>>> @wrds = split(" ", $words);
BR>>> foreach $w ( @wrds ) {
BR>>> $found = 0 if $text ~= /\b$w\b/i;
BR>>> }
BR>>> не находит даже "по закону"
EG>> Hет, находит - если исправить ошибки (=~ вместо ~=)
BR> Опечатка в тексте письма. В коде правильно.
EG>> и вообще писать аккуратно. И почитать perldoc perlre.
BR> Там сказано, что \b{} для юникода работает начиная с версии 5.22.

\b{} не то же самое, что \b

EG>> #!/usr/local/bin/perl
EG>> use 5.22.0;
BR> \b тоже только с 5.22 работает?

Hет.

BR> В любом случае, в перлхуке HPT не получается
BR> использовать use 5.22.0;, т.к. ругается на необявление всех переменных, в
BR> т.ч. и
BR> вшитых в HPT перлхук.

Hе думаю, что это из-за use 5.22.0 - скорее, из-за use strict.
Hо use strict по умолчанию врубает целую пачку разных проверок,
каждый тип проверки выдаёт своё сообщение. Так что показывай,
что конкретно пишет.

И в любом случае, можно обойтись и без use strict как такового -
это не имеет прямого отношения к \b.

BR> [...skipped...]
EG>> \b обозначает границу слова в регулярных выражениях.
EG>> backspace оно обозначает внутри классов символов (в квадратных скобках)
EG>> и вне регулярных выражений при интерполяции строк.
BR> Вот, а еще сказано, что m// обрабатывается так же, как строка в двойных
BR> кавычках и там возможа подстановка переменных. Это меня и смутило.

Цитату в студию.

Eugene
--
Поэты - страшные люди. У них все святое.

Michael Dukelsky

unread,
Jun 10, 2019, 9:55:01 AM6/10/19
to
Привет, Eugene!

10 June 2019 03:27, Eugene Grosbein послал(а) письмо к Brother Rabbit:

EG> #!/usr/local/bin/perl

EG> use 5.22.0;
EG> use strict;
EG> use warnings;
EG> use locale;

EG> my @wrds = qw(по закону);
EG> my $w;
EG> foreach $w ( @wrds ) {
EG> print "Hайдено: $w\n" if $ARGV[0] =~ /\b$w\b/i;
EG> }

EG> $ ./find.pl "по новому закону"
EG> Hайдено: по
EG> Hайдено: закону
EG> $ ./find.pl "гипопотам не указ закону"
EG> Hайдено: закону
EG> $ ./find.pl "по закону"
EG> Hайдено: по
EG> Hайдено: закону


EG> \b обозначает границу слова в регулярных выражениях.
EG> backspace оно обозначает внутри классов символов (в квадратных
EG> скобках) и вне регулярных выражений при интерполяции строк.

В 5.16 это не работает. Если закомментировать строчку "use 5.22.0;", то
получаем

$ ./find.pl "по новому закону"
по новому закону
$ ./find.pl "гипопотам не указ закону"
гипопотам не указ закону
$ ./find.pl "по закону"
по закону

Желаю успехов, Eugene!

Eugene Grosbein

unread,
Jun 10, 2019, 3:10:01 PM6/10/19
to
10 июня 2019, понедельник, в 16:50 NOVT, Michael Dukelsky написал(а):

EG>> #!/usr/local/bin/perl
EG>> use 5.22.0;
EG>> use strict;
EG>> use warnings;
EG>> use locale;
EG>> my @wrds = qw(по закону);
EG>> my $w;
EG>> foreach $w ( @wrds ) {
EG>> print "Hайдено: $w\n" if $ARGV[0] =~ /\b$w\b/i;
EG>> }
EG>> $ ./find.pl "по новому закону"
EG>> Hайдено: по
EG>> Hайдено: закону
EG>> $ ./find.pl "гипопотам не указ закону"
EG>> Hайдено: закону
EG>> $ ./find.pl "по закону"
EG>> Hайдено: по
EG>> Hайдено: закону
EG>> \b обозначает границу слова в регулярных выражениях.
EG>> backspace оно обозначает внутри классов символов (в квадратных
EG>> скобках) и вне регулярных выражений при интерполяции строк.
MD> В 5.16 это не работает. Если закомментировать строчку "use 5.22.0;", то
MD> получаем
MD> $ ./find.pl "по новому закону"
MD> по новому закону
MD> $ ./find.pl "гипопотам не указ закону"
MD> гипопотам не указ закону
MD> $ ./find.pl "по закону"
MD> по закону

Очевидно, что твой код отличается от процитированного
далеко не только отсутствием use 5.22.0 - как минимум,
процитированный код добавляет к каждой выдаваемой строчке
"Hайдено:". Может быть, ты убрал ещё и use locale,
а может быть, ты запускаешь его в ненастроенном окружении -
когда не выставлена локаль, соответствующая кодировке
текста скрипта. Или черт знает какие ещё отличия,
потому что и в 5.16 оно работать должно.

А может быть, ты запускаешь на системе, в которой вообще
не установленно русских локалей и тогда у perl нет информации
о том, какие из символов являются русскими буквами,
чтобы различать границу слова. Пример запуска на такой системе:

$ env LANG=ru_RU.KOI8-R ./find.pl "по новому закону"
perl: warning: Setting locale failed.
perl: warning: Please check that your locale settings:
LANGUAGE = (unset),
LC_ALL = (unset),
LANG = "ru_RU.KOI8-R"
are supported and installed on your system.
perl: warning: Falling back to the standard locale ("C").

Eugene
--
Hаучить не кланяться авторитетам, а исследовать их и сравнивать их поучения
с жизнью. Hаучить настороженно относиться к опыту бывалых людей, потому что
жизнь меняется необычайно быстро.

Eugene Grosbein

unread,
Jun 10, 2019, 3:10:01 PM6/10/19
to
10 июня 2019, понедельник, в 16:50 NOVT, Michael Dukelsky написал(а):

EG>> #!/usr/local/bin/perl
EG>> use 5.22.0;
EG>> use strict;
EG>> use warnings;
EG>> use locale;
EG>> my @wrds = qw(по закону);
EG>> my $w;
EG>> foreach $w ( @wrds ) {
EG>> print "Hайдено: $w\n" if $ARGV[0] =~ /\b$w\b/i;
EG>> }
EG>> $ ./find.pl "по новому закону"
EG>> Hайдено: по
EG>> Hайдено: закону
EG>> $ ./find.pl "гипопотам не указ закону"
EG>> Hайдено: закону
EG>> $ ./find.pl "по закону"
EG>> Hайдено: по
EG>> Hайдено: закону
EG>> \b обозначает границу слова в регулярных выражениях.
EG>> backspace оно обозначает внутри классов символов (в квадратных
EG>> скобках) и вне регулярных выражений при интерполяции строк.
MD> В 5.16 это не работает. Если закомментировать строчку "use 5.22.0;", то
MD> получаем
MD> $ ./find.pl "по новому закону"
MD> по новому закону
MD> $ ./find.pl "гипопотам не указ закону"
MD> гипопотам не указ закону
MD> $ ./find.pl "по закону"
MD> по закону

Работает и на 5.8.0:

$ ./find.pl "по новому закону"
Hайдено: по
Hайдено: закону
$ perl -v

This is perl, v5.8.0 built for i386-linux-thread-multi
(with 1 registered patch, see perl -V for more detail)

Eugene
--
Hароду - чтоб не вздумал бунтовать! -
Мы тоже разрешили воровать.
Пусть лучше сам ворует потихоньку,
Чем с воровскою властью враждовать!..

Michael Dukelsky

unread,
Jun 10, 2019, 4:30:00 PM6/10/19
to
Привет, Eugene!

11 June 2019 01:58, Eugene Grosbein послал(а) письмо к Michael Dukelsky:

EG> Очевидно, что твой код отличается от процитированного
EG> далеко не только отсутствием use 5.22.0

Да, действительно, я добавил print "$ARGV[0]\n"; а потом меня отвлекли и я
забыл про эту строчку.

#!/usr/bin/perl

#use 5.22.0;
use strict;
use warnings;
use locale;

print "$ARGV[0]\n";
my @wrds = qw(по закону);
my $w;
foreach $w ( @wrds ) {
print "Найдено: $w\n" if $ARGV[0] =~ /\b$w\b/i;
}

То есть получается, что ничего не найдено.

EG> Может быть, ты убрал ещё и use locale,
EG> а может быть, ты запускаешь его в ненастроенном окружении -
EG> когда не выставлена локаль, соответствующая кодировке
EG> текста скрипта. Или черт знает какие ещё отличия,
EG> потому что и в 5.16 оно работать должно.

$ locale
LANG=ru_RU.UTF-8
LC_CTYPE="ru_RU.UTF-8"
LC_NUMERIC="ru_RU.UTF-8"
LC_TIME=ru_RU.UTF-8
LC_COLLATE="ru_RU.UTF-8"
LC_MONETARY="ru_RU.UTF-8"
LC_MESSAGES=ru_RU.UTF-8
LC_PAPER="ru_RU.UTF-8"
LC_NAME="ru_RU.UTF-8"
LC_ADDRESS="ru_RU.UTF-8"
LC_TELEPHONE="ru_RU.UTF-8"
LC_MEASUREMENT="ru_RU.UTF-8"
LC_IDENTIFICATION="ru_RU.UTF-8"
LC_ALL=

Eugene Grosbein

unread,
Jun 10, 2019, 5:00:01 PM6/10/19
to
10 июня 2019, понедельник, в 23:03 NOVT, Michael Dukelsky написал(а):

MD> $ locale
MD> LANG=ru_RU.UTF-8

utf8 это принципиально отличается от старых однобайтовых локалей,
поэтому требует ещё и use utf8;

Eugene

Michael Dukelsky

unread,
Jun 11, 2019, 9:45:01 AM6/11/19
to
Привет, Eugene!

11 June 2019 03:53, Eugene Grosbein послал(а) письмо к Michael Dukelsky:

MD>> $ locale
MD>> LANG=ru_RU.UTF-8

EG> utf8 это принципиально отличается от старых однобайтовых локалей,
EG> поэтому требует ещё и use utf8;

Не помогло. Однако, если анализируемый текст брать не из командной строки, то
работает.

#!/usr/bin/perl

#use 5.22.0;
use strict;
use warnings;
use locale;
use utf8;

my $text = "гипопотам не указ закону";
my @wrds = qw(по закону);
my $w;
foreach $w ( @wrds ) {
print "Найдено: $w\n" if $text =~ /\b$w\b/i;
}

$ ./find.pl
Wide character in print at ./find.pl line 13.
Найдено: закону

Michael Dukelsky

unread,
Jun 11, 2019, 9:45:01 AM6/11/19
to
Привет, Eugene!

11 June 2019 13:25, Michael Dukelsky послал(а) письмо к Eugene Grosbein:

MD> Не помогло. Однако, если анализируемый текст брать не из командной
MD> строки, то работает.

Надо было внимательнее читать perlrun. :)

#!/usr/bin/perl

use strict;
use warnings;
use locale;
use utf8;

my @wrds = qw(по закону);
my $w;
foreach $w ( @wrds ) {
print "Найдено: $w\n" if $ARGV[0] =~ /\b$w\b/i;
}

$ perl -CAO ./find.pl "гипопотам не указ закону"

Brother Rabbit

unread,
Jun 11, 2019, 11:55:01 AM6/11/19
to
Hi, Eugene!

10 июн 19 16:36, Eugene Grosbein -> Brother Rabbit:

BR>> Опечатка в тексте письма. В коде правильно.
EG>>> и вообще писать аккуратно. И почитать perldoc perlre.
BR>> Там сказано, что \b{} для юникода работает начиная с версии 5.22.

EG> \b{} не то же самое, что \b

Я знаю.

EG>>> #!/usr/local/bin/perl
EG>>> use 5.22.0;
BR>> \b тоже только с 5.22 работает?

EG> Hет.

Ну, вот, у меня не работает.

[fido@BroRabbit ~]$ perl -v

This is perl 5, version 22, subversion 3 (v5.22.3) built for
x86_64-linux-thread-multi

BR>> В любом случае, в перлхуке HPT не получается
BR>> использовать use 5.22.0;, т.к. ругается на необявление всех переменных, в
BR>> т.ч. и вшитых в HPT перлхук.

EG> Hе думаю, что это из-за use 5.22.0 - скорее, из-за use strict.

Именно с включением этого появляется, с выключением пропадает.

EG> Hо use strict по умолчанию врубает целую пачку разных проверок,
EG> каждый тип проверки выдаёт своё сообщение. Так что показывай,
EG> что конкретно пишет.

6 07:42:01 PERL: Global symbol "%config" requires explicit package name (did
you forget to declare "my %config"?) at /home/fido/perl/fidogle.pm line 82.
6 07:42:01 PERL: Global symbol "$warn_addr" requires explicit package name
(did you forget to declare "my $warn_addr"?) at /home/fido/perl/fidogle.pm line
82.
6 07:42:01 PERL: Global symbol "$UNS" requires explicit package name (did you
forget to declare "my $UNS"?) at /home/fido/perl/fidogle.pm line 83.
6 07:42:01 PERL: Global symbol "$from_name" requires explicit package name
(did you forget to declare "my $from_name"?) at /home/fido/perl/fidogle.pm line
83.
6 07:42:01 PERL: Global symbol "@Via" requires explicit package name (did you
forget to declare "my @Via"?) at /home/fido/perl/fidogle.pm line 84.
6 07:42:01 PERL: Global symbol "$hpt_version" requires explicit package name
(did you forget to declare "my $hpt_version"?) at /home/fido/perl/fidogle.pm
line 85.
6 07:42:01 PERL: Global symbol "%config" requires explicit package name (did
you forget to declare "my %config"?) at /home/fido/perl/fidogle.pm line 85.
6 07:42:01 PERL: Global symbol "%config" requires explicit package name (did
you forget to declare "my %config"?) at /home/fido/perl/fidogle.pm line 85.


BR>> [...skipped...]
EG>>> \b обозначает границу слова в регулярных выражениях.
EG>>> backspace оно обозначает внутри классов символов (в квадратных скобках)
EG>>> и вне регулярных выражений при интерполяции строк.
BR>> Вот, а еще сказано, что m// обрабатывается так же, как строка в двойных
BR>> кавычках и там возможа подстановка переменных. Это меня и смутило.

EG> Цитату в студию.

Я за эту неделю столько доки по этой теме выкурил, что сейчас и не вспомню, в
которой так было сказано.

Brother Rabbit

unread,
Jun 11, 2019, 11:55:01 AM6/11/19
to
Hi, Eugene!

11 июн 19 03:53, Eugene Grosbein -> Michael Dukelsky:

MD>> $ locale
MD>> LANG=ru_RU.UTF-8

EG> utf8 это принципиально отличается от старых однобайтовых локалей,
EG> поэтому требует ещё и use utf8;

[fido@BroRabbit ~]$ locale
LANG=ru_RU.IBM866
LC_CTYPE="ru_RU.IBM866"
LC_NUMERIC="ru_RU.IBM866"
LC_TIME="ru_RU.IBM866"
LC_COLLATE="ru_RU.IBM866"
LC_MONETARY="ru_RU.IBM866"
LC_MESSAGES="ru_RU.IBM866"
LC_PAPER="ru_RU.IBM866"
LC_NAME="ru_RU.IBM866"
LC_ADDRESS="ru_RU.IBM866"
LC_TELEPHONE="ru_RU.IBM866"
LC_MEASUREMENT="ru_RU.IBM866"
LC_IDENTIFICATION="ru_RU.IBM866"
LC_ALL=

Eugene Grosbein

unread,
Jun 11, 2019, 2:45:01 PM6/11/19
to
11 июня 2019, вторник, в 18:37 NOVT, Brother Rabbit написал(а):

BR>>> Опечатка в тексте письма. В коде правильно.
EG>>>> и вообще писать аккуратно. И почитать perldoc perlre.
BR>>> Там сказано, что \b{} для юникода работает начиная с версии 5.22.
EG>> \b{} не то же самое, что \b
BR> Я знаю.
EG>>>> #!/usr/local/bin/perl
EG>>>> use 5.22.0;
BR>>> \b тоже только с 5.22 работает?
EG>> Hет.
BR> Hу, вот, у меня не работает.

У тебя, наверное, используется utf8 и обращаешься ты с ним неаккуратно,
без use utf8 и т.д.

BR> [fido@BroRabbit ~]$ perl -v
BR> This is perl 5, version 22, subversion 3 (v5.22.3) built for
BR> x86_64-linux-thread-multi
BR>>> В любом случае, в перлхуке HPT не получается
BR>>> использовать use 5.22.0;, т.к. ругается на необявление всех переменных,
BR>>> в
BR>>> т.ч. и вшитых в HPT перлхук.
EG>> Hе думаю, что это из-за use 5.22.0 - скорее, из-за use strict.
BR> Именно с включением этого появляется, с выключением пропадает.

perldoc use сообщает, то use 5.12.0 или больше врубает и use strict для
структур, так что либо не используй use 5.22.0, либо добавь no strict.

BR>>> Вот, а еще сказано, что m// обрабатывается так же, как строка в двойных
BR>>> кавычках и там возможа подстановка переменных. Это меня и смутило.
EG>> Цитату в студию.
BR> Я за эту неделю столько доки по этой теме выкурил, что сейчас и не
BR> вспомню, в
BR> которой так было сказано.

В общем, это не так.

Eugene
--
Choose no career

Eugene Grosbein

unread,
Jun 11, 2019, 2:50:02 PM6/11/19
to
11 июня 2019, вторник, в 18:43 NOVT, Brother Rabbit написал(а):

MD>>> $ locale
MD>>> LANG=ru_RU.UTF-8
EG>> utf8 это принципиально отличается от старых однобайтовых локалей,
EG>> поэтому требует ещё и use utf8;
BR> [fido@BroRabbit ~]$ locale
BR> LANG=ru_RU.IBM866
BR> LC_CTYPE="ru_RU.IBM866"
BR> LC_NUMERIC="ru_RU.IBM866"
BR> LC_TIME="ru_RU.IBM866"
BR> LC_COLLATE="ru_RU.IBM866"
BR> LC_MONETARY="ru_RU.IBM866"
BR> LC_MESSAGES="ru_RU.IBM866"
BR> LC_PAPER="ru_RU.IBM866"
BR> LC_NAME="ru_RU.IBM866"
BR> LC_ADDRESS="ru_RU.IBM866"
BR> LC_TELEPHONE="ru_RU.IBM866"
BR> LC_MEASUREMENT="ru_RU.IBM866"
BR> LC_IDENTIFICATION="ru_RU.IBM866"
BR> LC_ALL=

Если use locale при этом не ругается - то есть, такая локаль
в системе установлена (что не факт, у меня оно ru_RU.CP866),
то значит - локаль битая, то есть определения ctype в ней
неправильные. Попробуй для теста выставить другую локаль -
обычно ru_RU.KOI8-R у все корректная, если есть вообще,
затем перекодируй всё для проверки в KOi8-R и потестируй.

Hу или utf8 вместо koi. Если заработает - проблема в твоём
дистрибутиве, который имеет кривую локаль для cp866.

Eugene

Brother Rabbit

unread,
Jun 11, 2019, 4:20:01 PM6/11/19
to
Hi, Eugene!

12 июн 19 01:31, Eugene Grosbein -> Brother Rabbit:

BR>>>> Опечатка в тексте письма. В коде правильно.
EG>>>>> и вообще писать аккуратно. И почитать perldoc perlre.
BR>>>> Там сказано, что \b{} для юникода работает начиная с версии 5.22.
EG>>> \b{} не то же самое, что \b
BR>> Я знаю.
EG>>>>> #!/usr/local/bin/perl
EG>>>>> use 5.22.0;
BR>>>> \b тоже только с 5.22 работает?
EG>>> Hет.
BR>> Hу, вот, у меня не работает.

EG> У тебя, наверное, используется utf8 и обращаешься ты с ним неаккуратно,
EG> без use utf8 и т.д.

Нету у меня там utf8. Там cp866 в какчестве локали стоит и ьаза в ней же.

BR>> [fido@BroRabbit ~]$ perl -v
BR>> This is perl 5, version 22, subversion 3 (v5.22.3) built for
BR>> x86_64-linux-thread-multi
BR>>>> В любом случае, в перлхуке HPT не получается
BR>>>> использовать use 5.22.0;, т.к. ругается на необявление всех переменных,
BR>>>> в т.ч. и вшитых в HPT перлхук.
EG>>> Hе думаю, что это из-за use 5.22.0 - скорее, из-за use strict.
BR>> Именно с включением этого появляется, с выключением пропадает.

EG> perldoc use сообщает, то use 5.12.0 или больше врубает и use strict для
EG> структур, так что либо не используй use 5.22.0, либо добавь no strict.

О! Нужно попробовать. Кстати, методом научного тыка выяснилось, что глюк
вспылвает, если испольщовать use 5.22.0 в .pm, если в скрипте, его вызывающем,
то не ругается. Правда, в HPT-шном filter.pl я еще не пробовал.

BR>>>> Вот, а еще сказано, что m// обрабатывается так же, как строка в
BR>>>> двойных
BR>>>> кавычках и там возможа подстановка переменных. Это меня и смутило.
EG>>> Цитату в студию.
BR>> Я за эту неделю столько доки по этой теме выкурил, что сейчас и не
BR>> вспомню, в которой так было сказано.

EG> В общем, это не так.

Ну, я уже понял.

Brother Rabbit

unread,
Jun 12, 2019, 2:05:01 AM6/12/19
to
Hi, Eugene!

12 июн 19 01:36, Eugene Grosbein -> Brother Rabbit:

MD>>>> $ locale

[...skipped...]

EG> Если use locale при этом не ругается - то есть, такая локаль

Не ругается.

EG> в системе установлена (что не факт, у меня оно ru_RU.CP866),
EG> то значит - локаль битая, то есть определения ctype в ней
EG> неправильные. Попробуй для теста выставить другую локаль -
EG> обычно ru_RU.KOI8-R у все корректная, если есть вообще,
EG> затем перекодируй всё для проверки в KOi8-R и потестируй.

EG> Hу или utf8 вместо koi. Если заработает - проблема в твоём
EG> дистрибутиве, который имеет кривую локаль для cp866.

С локалью все в порядке, я думаю. Регистронезависимый поиск в русском языке
работает с use locale; и не работает без этого. Однако, \b почему-то не
находится даже с use 5.22.0.

Michael Dukelsky

unread,
Jun 12, 2019, 11:10:01 AM6/12/19
to
Привет, Brother!

12 June 2019 08:45, Brother Rabbit послал(а) письмо к Eugene Grosbein:

BR> С локалью все в порядке, я думаю. Регистронезависимый поиск в русском
BR> языке работает с use locale; и не работает без этого. Однако, \b
BR> почему-то не находится даже с use 5.22.0.

Попробуй временно вставить в свой скрипт
print "unicode=${^UNICODE}\n";

Если напечатает не 0, то попробуй запустить скрипт через perl -C0

Желаю успехов, Brother!

Eugene Grosbein

unread,
Jun 13, 2019, 5:55:01 AM6/13/19
to
12 июня 2019, среда, в 08:45 NOVT, Brother Rabbit написал(а):

BR> С локалью все в порядке, я думаю. Регистронезависимый поиск в русском
BR> языке
BR> работает с use locale; и не работает без этого.

Это ничего не значит. В локали вполне может быть правильный
collation (данные регистре), но кривой ctype - такое встречалось.

Имя IBM866 (вместо стандартного CP866) намекает на то,
что вместо полноценной локали у тебя какой-то самопал недоделанный.

BR> Однако, \b почему-то не находится даже с use 5.22.0.

Это не проблема перла, это проблема используемой системной локали.

Eugene

Alexey Vissarionov

unread,
Jun 13, 2019, 3:20:01 PM6/13/19
to
Доброго времени суток, Eugene!
13 Jun 2019 16:37:32, ты -> Brother Rabbit:

BR>> С локалью все в порядке, я думаю. Регистронезависимый поиск в
BR>> русском языке работает с use locale; и не работает без этого.
EG> Это ничего не значит. В локали вполне может быть правильный
EG> collation (данные регистре), но кривой ctype - такое встречалось.
EG> Имя IBM866 (вместо стандартного CP866) намекает на то, что вместо
EG> полноценной локали у тебя какой-то самопал недоделанный.

И на то, что ТС начисто проигнорировал рекомендации держать фидошный софт в
локали KOI8-R.

BR>> Однако, \b почему-то не находится даже с use 5.22.0.
EG> Это не проблема перла, это проблема используемой системной локали.

Локаль - свойство процесса, а не системы.


--
Alexey V. Vissarionov aka Gremlin from Kremlin
gremlin ПРИ gremlin ТЧК ru; +vii-cmiii-ccxxix-lxxix-xlii

... - Что вы чувствуете, когда стреляете в людей? - Отдачу.

Eugene Grosbein

unread,
Jun 13, 2019, 6:50:01 PM6/13/19
to
13 июня 2019, четверг, в 22:11 NOVT, Alexey Vissarionov написал(а):

BR>>> Однако, \b почему-то не находится даже с use 5.22.0.
EG>> Это не проблема перла, это проблема используемой системной локали.
AV> Локаль - свойство процесса, а не системы.

Hе противоречит. Данные локали обычно часть системы,
процессы не таскают определения collation/ctype/etc. с собой.

Eugene

Stas Mishchenkov

unread,
Jul 9, 2019, 3:45:02 AM7/9/19
to
Hi, Alexey!

13 июн 19 22:11, Alexey Vissarionov -> Eugene Grosbein:

AV> И на то, что ТС начисто проигнорировал рекомендации держать фидошный
AV> софт в локали KOI8-R.

Объясни простым языком, зачем нужна двойная перекодировка?

Have nice nights.
Stas Mishchenkov.

Eugene Grosbein

unread,
Jul 9, 2019, 6:35:01 AM7/9/19
to
09 июля 2019, вторник, в 10:41 NOVT, Stas Mishchenkov написал(а):

AV>> И на то, что ТС начисто проигнорировал рекомендации держать фидошный
AV>> софт в локали KOI8-R.
SM> Объясни простым языком, зачем нужна двойная перекодировка?

Чтобы корректно работал софт, заточенный только под KOI8-R
и который никто уже не будет переписывать под другие кодировки.

Stas Mishchenkov

unread,
Jul 10, 2019, 3:05:01 AM7/10/19
to
Hi, Eugene!

09 июл 19 17:15, Eugene Grosbein -> Stas Mishchenkov:

AV>>> И на то, что ТС начисто проигнорировал рекомендации держать фидошный
AV>>> софт в локали KOI8-R.
SM>> Объясни простым языком, зачем нужна двойная перекодировка?

EG> Чтобы корректно работал софт, заточенный только под KOI8-R
EG> и который никто уже не будет переписывать под другие кодировки.

т.е. ты хочешь сказать, что если у меня перловый скрипт корректно отрабатывает
вот такой код:

use locale;

@wrds = split(' ', $s_words);
foreach $w ( @wrds ) {
if ( $msgtext =~ /(.{0,10})\b($w)\b(.{0,10})/si ) {
print "Found: $1__$2__$3\n";
} else { print "\'$w\' not found.\n"; }
}

и при этом тот же код не работает в прелхуке HPT, то в KOI8-R все будет
работать и там?

Eugene Grosbein

unread,
Jul 10, 2019, 6:10:02 AM7/10/19
to
10 июля 2019, среда, в 09:53 NOVT, Stas Mishchenkov написал(а):

AV>>>> И на то, что ТС начисто проигнорировал рекомендации держать фидошный
AV>>>> софт в локали KOI8-R.
SM>>> Объясни простым языком, зачем нужна двойная перекодировка?
EG>> Чтобы корректно работал софт, заточенный только под KOI8-R
EG>> и который никто уже не будет переписывать под другие кодировки.
SM> т.е. ты хочешь сказать, что если у меня перловый скрипт корректно
SM> отрабатывает
SM> вот такой код:
SM> use locale;
SM> @wrds = split(' ', $s_words);
SM> foreach $w ( @wrds ) {
SM> if ( $msgtext =~ /(.{0,10})\b($w)\b(.{0,10})/si ) {
SM> print "Found: $1__$2__$3\n";
SM> } else { print "\'$w\' not found.\n"; }
SM> }
SM> и при этом тот же код не работает в прелхуке HPT, то в KOI8-R все будет
SM> работать и там?

Без понятия, надо тестировать. Hо у меня есть код, который вынужден
работать с данными в неизвестной внешней кодировке в отсутствие метаданных.
В норме там обычно приходит windows-1251, но из-за багов может поступить
сырой utf-8 и код обрабатывает оба случая, приводя всё к общему знаменателю.
Исходные данные в переменной $tmp:

# detect UTF-8 encoding, otherwise assume 8-bit windows-1251
# Convert to internal Perl unicode
$tmp = $s1 = utf8::decode($tmp) ? $tmp :
Encode::decode('windows-1251', $s1, Encode::FB_PERLQQ);

Можешь что-то подобное нарисовать и себе.
Hо у меня код работает *без* use locale (мне не надо делать word splitting).

Eugene
--
Устав от вечных упований,
Устав от радостных пиров

Stas Mishchenkov

unread,
Jul 13, 2019, 4:25:01 PM7/13/19
to
Hi, Eugene!

10 июл 19 16:59, Eugene Grosbein -> Stas Mishchenkov:

AV>>>>> И на то, что ТС начисто проигнорировал рекомендации держать
AV>>>>> фидошный
AV>>>>> софт в локали KOI8-R.
SM>>>> Объясни простым языком, зачем нужна двойная перекодировка?
EG>>> Чтобы корректно работал софт, заточенный только под KOI8-R
EG>>> и который никто уже не будет переписывать под другие кодировки.
SM>> т.е. ты хочешь сказать, что если у меня перловый скрипт корректно
SM>> отрабатывает вот такой код: use locale;
SM>> @wrds = split(' ', $s_words);
SM>> foreach $w ( @wrds ) {
SM>> if ( $msgtext =~ /(.{0,10})\b($w)\b(.{0,10})/si ) {
SM>> print "Found: $1__$2__$3\n";
SM>> } else { print "\'$w\' not found.\n"; }
SM>> }
SM>> и при этом тот же код не работает в прелхуке HPT, то в KOI8-R все будет
SM>> работать и там?

EG> Без понятия, надо тестировать.

Вот и я думаю, что это глюк реализации пердла в HPT.

EG> Hо у меня есть код, который вынужден работать с данными в неизвестной
EG> внешней кодировке в отсутствие метаданных. В норме там обычно приходит
EG> windows-1251, но из-за багов может поступить сырой utf-8 и код
EG> обрабатывает оба случая, приводя всё к общему
EG> знаменателю. Исходные данные в переменной $tmp:

EG> # detect UTF-8 encoding, otherwise assume 8-bit windows-1251
EG> # Convert to internal Perl unicode
EG> $tmp = $s1 = utf8::decode($tmp) ? $tmp :
EG> Encode::decode('windows-1251', $s1, Encode::FB_PERLQQ);

EG> Можешь что-то подобное нарисовать и себе.

Но у меня-то кодировка выв базе известна.

EG> Hо у меня код работает *без* use locale (мне не надо делать word
EG> splitting).

А мне как раз нужно split и \b$word\b юзать, а для этого use locale;.

Eugene Grosbein

unread,
Jul 14, 2019, 10:05:01 AM7/14/19
to
13 июля 2019, суббота, в 23:18 NOVT, Stas Mishchenkov написал(а):

SM> Вот и я думаю, что это глюк реализации пердла в HPT.

Я очень сильно сомневаюсь, что в HPT есть своя реализация perl
или перловского word splitting. Мне не очень понятно,
почему ты игнорируешь информацию о том, как именно работает
word splitting в perl и почему ты до сих пор не потестировал,
как было предложено. Такое ощущение, что тебе проблему решать и не надо.

Stas Mishchenkov

unread,
Jul 17, 2019, 5:05:01 AM7/17/19
to
Hi, Eugene!

14 июл 19 20:54, Eugene Grosbein -> Stas Mishchenkov:

SM>> Вот и я думаю, что это глюк реализации пердла в HPT.

EG> Я очень сильно сомневаюсь, что в HPT есть своя реализация perl
EG> или перловского word splitting.

Будем точнее. Реализация перлхуков.

EG> Мне не очень понятно, почему ты игнорируешь информацию о том, как
EG> именно работает word splitting в perl и почему ты до сих пор не
EG> потестировал, как было предложено. Такое ощущение, что тебе проблему
EG> решать и не надо.

Между тем мой эмпириокритицизм позволил мне все-таки найти корень проблемы.

#!/usr/bin/perl

use POSIX;
use locale;
my $old_locale;

$old_locale = setlocale(LC_CTYPE);
print "$old_locale\n";

в командной строке печатает ru_RU.IBM866, а в filter.pl

use POSIX;
use locale;
my $old_locale;

$old_locale = setlocale(LC_CTYPE);
w_log( "locale: $old_locale\n" );

пишет в лог "locale: С".

Eugene Grosbein

unread,
Jul 17, 2019, 7:40:01 AM7/17/19
to
17 июля 2019, среда, в 10:49 NOVT, Stas Mishchenkov написал(а):

SM> Между тем мой эмпириокритицизм позволил мне все-таки найти корень
SM> проблемы.
SM> #!/usr/bin/perl
SM> use POSIX;
SM> use locale;
SM> my $old_locale;
SM> $old_locale = setlocale(LC_CTYPE);
SM> print "$old_locale\n";
SM> в командной строке печатает ru_RU.IBM866, а в filter.pl
SM> use POSIX;
SM> use locale;
SM> my $old_locale;
SM> $old_locale = setlocale(LC_CTYPE);
SM> w_log( "locale: $old_locale\n" );
SM> пишет в лог "locale: С".

90% за то, что система запускает бинарник без выставления локали.

Stas Mishchenkov

unread,
Jul 18, 2019, 2:35:01 AM7/18/19
to
Hi, Eugene!

17 июл 19 18:27, Eugene Grosbein -> Stas Mishchenkov:

SM>> Между тем мой эмпириокритицизм позволил мне все-таки найти корень
SM>> проблемы. #!/usr/bin/perl use POSIX; use locale; my $old_locale;
SM>> $old_locale = setlocale(LC_CTYPE);
SM>> print "$old_locale\n";
SM>> в командной строке печатает ru_RU.IBM866, а в filter.pl
SM>> use POSIX;
SM>> use locale;
SM>> my $old_locale;
SM>> $old_locale = setlocale(LC_CTYPE);
SM>> w_log( "locale: $old_locale\n" );
SM>> пишет в лог "locale: С".

EG> 90% за то, что система запускает бинарник без выставления локали.

Гм. Он у меня действительно по крону запускается от имени пользователя fido, у
которого, впрочем, локаль установлена нужная.

Alexey Vissarionov

unread,
Jul 18, 2019, 5:45:01 AM7/18/19
to
Доброго времени суток, Stas!
18 Jul 2019 09:27:28, ты -> Eugene Grosbein:

SM>>> пишет в лог "locale: С".
EG>> 90% за то, что система запускает бинарник без выставления локали.
SM> Гм. Он у меня действительно по крону запускается от имени пользователя
SM> fido, у которого, впрочем, локаль установлена нужная.

Локаль - свойство процесса, а не пользователя и уж тем более не системы.


--
Alexey V. Vissarionov aka Gremlin from Kremlin
gremlin ПРИ gremlin ТЧК ru; +vii-cmiii-ccxxix-lxxix-xlii

... Чем умные отличаются от дураков? Умные дурачатся, а дураки умничают.

Eugene Grosbein

unread,
Jul 18, 2019, 7:10:01 AM7/18/19
to
18 июля 2019, четверг, в 09:27 NOVT, Stas Mishchenkov написал(а):

SM>>> Между тем мой эмпириокритицизм позволил мне все-таки найти корень
SM>>> проблемы. #!/usr/bin/perl use POSIX; use locale; my $old_locale;
SM>>> $old_locale = setlocale(LC_CTYPE);
SM>>> print "$old_locale\n";
SM>>> в командной строке печатает ru_RU.IBM866, а в filter.pl
SM>>> use POSIX;
SM>>> use locale;
SM>>> my $old_locale;
SM>>> $old_locale = setlocale(LC_CTYPE);
SM>>> w_log( "locale: $old_locale\n" );
SM>>> пишет в лог "locale: С".
EG>> 90% за то, что система запускает бинарник без выставления локали.
SM> Гм. Он у меня действительно по крону запускается от имени пользователя
SM> fido, у
SM> которого, впрочем, локаль установлена нужная.

Если не делать отдельных телодвижений, то локаль вместе со всем окружением
наследуется от процесса-родителя, в данном случае от крона.

Поменяй строку запуска "команда" на:

env LC_ALL=ru_RU.IBM866 команда

Eugene
0 new messages