perl libSqliteIcu.so сопоставить icu
LibSqliteIcu прекрасно работает в терминале sqlite3 с:
sqlite3
...
.load './libSqliteIcu.so'
SELECT icu_load_collation('pl_PL', 'POLISH');
SELECT DISTINCT miasto FROM tab ORDER BY miasto COLLATE POLISH;
Как кодировать последовательность выше в Perl?
2 ответа
Непроверенные:
use DBI qw();
my $dbh = DBI->connect('DBI:SQLite:thedatabase.sqlite');
$dbh->sqlite_enable_load_extension(1);
$dbh->do(q{SELECT load_extension('./libSqliteIcu.so')});
$dbh->do(q{SELECT icu_load_collation('pl_PL', 'POLISH')};
my $miasto = $dbh->selectall_arrayref(q{SELECT DISTINCT miasto FROM tab ORDER BY miasto COLLATE POLISH});
Также можно отсортировать в Perl:
use utf8;
my @tongue_twister = qw(Król Karol kupił królowej Karolinie korale koloru koralowego);
use Unicode::ICU::Collator qw(); # ICU C library, fast
my $c = Unicode::ICU::Collator->new('pl_PL');
use Unicode::Collate qw(); # pure-perl, slow
my $c = Unicode::Collate->new(locale => 'pl_PL');
my @sorted = $c->sort(@tongue_twister);
# (
# 'Karol',
# 'Karolinie',
# 'koloru',
# 'korale',
# 'koralowego',
# 'Król',
# 'królowej',
# 'kupił'
# )
Одним простым, но не идеальным решением является использование pl_PL.UTF8
локали.
В sqlite3 мы готовим:
create table A(idA);
...
insert into A values('ź');
insert into A values('Ż');
insert into A values('ź');
insert into A values('Š');
...
insert into A values('ś');
...
и сейчас:
select * from A;
дает: Z ź Ż ź z ś ż S Š z.
Итак, мы загружаем:
.load './libSqliteIcu.so'
SELECT icu_load_collation('pl_PL', 'POLISH');
select idA from A order by idA collate POLISH;
и мы имеем: S Š ś zz Z ź ź ż Ż.
Итак, теперь в Perl мы можем положить:
SELECT idA FROM A ORDER BY idA
и получите не правильный заказ: SZ zz ś Š ź ź Ż ż
Теперь с помощью perllocale мы помещаем в perl:
SELECT idA FROM A ORDER BY idA COLLATE perllocale
и получите заказ: S Š ś zz Z ź ź ż Ż.
$dbh->do(q{SELECT load_extension('./libSqliteIcu.so')});
не работает в моем случае; это делает ошибку:
DBD:: SQLite:: db do не удалось: невозможно удалить / изменить пользовательскую функцию из-за ошибки активных операторов во время инициализации