nicht Umlaute, aber fremdsprachige Zeichensätze

nicht Umlaute, aber fremdsprachige Zeichensätze

am 22.04.2006 19:27:16 von Ralph Stahl

Ich möchte eine Tabelle mit Texteinträgen (Spalte mit fulltext)
volltextlich durchsuchen (like oder rlike oder matches..against).
Die Einträge können aus vielen Sprachen kommen (auch Osteuropa oder
griechisch) daher werde ich die Tabelle/Spalte sicher mit utf8_bin
codieren. Die Suche soll case-insensitiv sein.

Beim normalen ASCII-Zeichensatz unterscheiden sich Groß- und
Kleinbuchstaben um 20hex, bei den genannten Zeichensätzen aber oft nur
um 10hex. Ich habe nichts finden können, ob und wie die
case-insensitiven Funktionen damit umgehen können. Das betrifft wohl
auch PHP-Funktionen wie strtoupper().

Wie muß ich es richtig machen, damit die Suche mit beliebigen Sprachen
funktioniert? Bin für jeden Tip dankbar, da sich das (auch wegen der
eigenen mangelnden Sprachkenntnisse) besch...eiden testen läßt.

Ralph

Re: nicht Umlaute, aber fremdsprachige Zeichensätze

am 22.04.2006 22:34:26 von Thomas Rachel

Ralph Stahl wrote:

> griechisch) daher werde ich die Tabelle/Spalte sicher mit utf8_bin
> codieren. Die Suche soll case-insensitiv sein.

Dann würde ich eher utf8_general nehmen.


> Beim normalen ASCII-Zeichensatz unterscheiden sich Groß- und
> Kleinbuchstaben um 20hex, bei den genannten Zeichensätzen aber oft nur
> um 10hex. Ich habe nichts finden können, ob und wie die
> case-insensitiven Funktionen damit umgehen können.

> Das betrifft wohl auch PHP-Funktionen wie strtoupper().

Inwieweit PHP mit utf8-Groß- und -Kleinschreibung umgehen kann, weiß ich
leider nicht. Dafür gibt es aber ebenfalls NGs, die Dir da sicher
weiterhelfen können.


> Wie muß ich es richtig machen, damit die Suche mit beliebigen Sprachen
> funktioniert? Bin für jeden Tip dankbar, da sich das (auch wegen der
> eigenen mangelnden Sprachkenntnisse) besch...eiden testen läßt.

NACK. Ich kann selbst kaum ein Wort Griechisch. Aber das hindert mich ja
nicht an Operationen mit einzelnen Buchstaben:


create temporary table ta (tx varchar(10));
show create table ta\G
*************************** 1. row ***************************
Table: ta
Create Table: CREATE TEMPORARY TABLE `ta` (
`tx` varchar(10) default NULL
) ENGINE=MyISAM DEFAULT CHARSET=utf8
1 row in set (0,00 sec)

insert into ta set tx=0xceb1;
insert into ta set tx=upper(0xceb1);
select tx from ta;
/* ups? 2x kleines Alpha? Hm, das upper hier wirkte offenbar nicht... */
set @al=0xceb1;
select upper(@al);
/* huch? auch nicht... */
select @al:=upper(tx) from ta limit 1;
/* ah! Sieht aber aus wie ein A... */
select hex(tx) from ta;
select hex(upper(tx)) from ta;
select hex(lower(tx)) from ta;
/* sind aber alles Alphas... */

/* und weils grad so schön war... ;-) */
insert into ta set tx=0xceb2;
insert into ta set tx=0xceb3;
insert into ta set tx=0xceb4;
insert into ta set tx=0xceb5;
insert into ta set tx=0xceb6;
insert into ta set tx=0xceb7;
insert into ta set tx=0xceb8;
insert into ta set tx=0xceb9;
insert into ta set tx=0xceba;
insert into ta set tx=0xcebb;
insert into ta set tx=0xcebc;
insert into ta set tx=0xcebd;
insert into ta set tx=0xcebe;
insert into ta set tx=0xcebf;
insert into ta set tx=0xcf80;
insert into ta set tx=0xcf81;
insert into ta set tx=0xcf82;
insert into ta set tx=0xcf83;
insert into ta set tx=0xcf84;
insert into ta set tx=0xcf85;
insert into ta set tx=0xcf86;
insert into ta set tx=0xcf87;
insert into ta set tx=0xcf88;
insert into ta set tx=0xcf89;
insert into ta set tx=0xcf8a;
insert into ta set tx=0xcf8b;
insert into ta set tx=0xcf8c;
insert into ta set tx=0xcf8d;
insert into ta set tx=0xcf8e;
insert into ta set tx=0xcf8f;
select upper(tx) from ta;
select hex(tx) from ta;
select hex(upper(tx)) from ta;
select hex(lower(tx)) from ta;


Bei den Griechen geht es offenbar. Ist zwar kein echter Beweis, daß es
dann bei den Polen, Tschechen, Ungarn,... auch geht, aber zumindest ein
Indiz.


HTH,

Thomas

Re: nicht Umlaute, aber fremdsprachige Zeichensätze

am 24.04.2006 12:17:50 von Ralph Stahl

Danke Dir! hast Dir viel Mühe gemacht :-).


In schrieb glglgl@expires-2006-05-
31.arcornews.de:
> Ralph Stahl wrote:
>=20
> > griechisch) daher werde ich die Tabelle/Spalte sicher mit utf8_bin
> > codieren. Die Suche soll case-insensitiv sein.
>=20
> Dann würde ich eher utf8_general nehmen.
>=20
>=20
> > Beim normalen ASCII-Zeichensatz unterscheiden sich Groß- und
> > Kleinbuchstaben um 20hex, bei den genannten Zeichensätzen aber oft nu=
r
> > um 10hex. Ich habe nichts finden können, ob und wie die
> > case-insensitiven Funktionen damit umgehen können.
>=20
> > Das betrifft wohl auch PHP-Funktionen wie strtoupper().
>=20
> Inwieweit PHP mit utf8-Groß- und -Kleinschreibung umgehen kann, weiß =
ich
> leider nicht. Dafür gibt es aber ebenfalls NGs, die Dir da sicher
> weiterhelfen können.
>=20
>=20
> > Wie muß ich es richtig machen, damit die Suche mit beliebigen Sprache=
n
> > funktioniert? Bin für jeden Tip dankbar, da sich das (auch wegen der
> > eigenen mangelnden Sprachkenntnisse) besch...eiden testen läßt.
>=20
> NACK. Ich kann selbst kaum ein Wort Griechisch. Aber das hindert mich ja
> nicht an Operationen mit einzelnen Buchstaben:
>=20
>=20
> create temporary table ta (tx varchar(10));
> show create table ta\G
> *************************** 1. row ***************************
> Table: ta
> Create Table: CREATE TEMPORARY TABLE `ta` (
> `tx` varchar(10) default NULL
> ) ENGINE=3DMyISAM DEFAULT CHARSET=3Dutf8
> 1 row in set (0,00 sec)
>=20
> insert into ta set tx=3D0xceb1;
> insert into ta set tx=3Dupper(0xceb1);
> select tx from ta;
> /* ups? 2x kleines Alpha? Hm, das upper hier wirkte offenbar nicht... */
> set @al=3D0xceb1;
> select upper(@al);
> /* huch? auch nicht... */
> select @al:=3Dupper(tx) from ta limit 1;
> /* ah! Sieht aber aus wie ein A... */
> select hex(tx) from ta;
> select hex(upper(tx)) from ta;
> select hex(lower(tx)) from ta;
> /* sind aber alles Alphas... */

Re: nicht Umlaute, aber fremdsprachige Zeichensätze

am 24.04.2006 22:46:57 von Thomas Rachel

Ralph Stahl wrote:

> Danke Dir! hast Dir viel Mühe gemacht :-).

Bitteschön, gern geschehn! (Die Datei mit den utf8-Codes der griechischen
Buchstaben habe ich irgendwo in meinem Homeverzeichnis rumliegen
gehabt...)

Dafür darfst Du Dir http://learn.to/quote/ anschauen. ;-)

Kleiner Tip: Text oben/Fullquote (TOFU) ist im Usenet nicht gern gesehen.


Thomas
--
Bildschirm löschen? Brennt er denn?

Re: nicht Umlaute, aber fremdsprachige Zeichensätze

am 26.04.2006 10:25:57 von Ralph Stahl

In schrieb glglgl@expires-2006-05-
31.arcornews.de:
> Bitteschön, gern geschehn! (Die Datei mit den utf8-Codes der griechisch=
en
> Buchstaben habe ich irgendwo in meinem Homeverzeichnis rumliegen
> gehabt...)

So, nun habe ich das ganze endlich probiert: mySQL 5 mit folgender=20
Ausgabe von show variables:

character_set_client | latin1 =
=20
character_set_connection | latin1 =
=20
character_set_database | latin1 =
=20
character_set_results | latin1 =
=20
character_set_server | utf8 =
=20
character_set_system | utf8 =
=20
collation_connection | latin1_swedish_ci =
=20
collation_database | latin1_general_ci =
=20
collation_server | utf8_general_ci =
=20

(Warum da immer swedish steht, hab ich noch nicht rausgefunden - wohl=20
aber, daß ich mit der 5er version nicht der einzige bin, der das sieht).

Und nun habe ich Dein Script laufenlassen und gemerkt, daß es *keinen*=20
Unterschied gibt zwischen=20

select hex(tx) from ta;
select hex(upper(tx)) from ta;

Und auch nicht bei=20

set @al=3D0xceb1;
select hex(@al);
select hex(upper(@al));

Also weder beim Speichern in der Datenbank noch beim direkten=20
"Umrechnen".

Auch nicht, wenn ich zu Fuß alle möglichen Kombinationen setze:

set character_set_connection=3Dutf8;
set character_set_database=3Dutf8;
set character_set_results=3Dutf8;

Was übersehe ich denn?

> Dafür darfst Du Dir http://learn.to/quote/ anschauen. ;-)
> Kleiner Tip: Text oben/Fullquote (TOFU) ist im Usenet nicht gern gesehen.

Ich wollte mich ja nur bedanken :-(.

Ralph

Re: nicht Umlaute, aber fremdsprachige Zeichensätze

am 26.04.2006 12:26:41 von Axel Schwenke

Ralph Stahl wrote:

> So, nun habe ich das ganze endlich probiert: mySQL 5 mit folgender
> Ausgabe von show variables:

> character_set_client | latin1
> character_set_connection | latin1
> character_set_results | latin1

Dein Client sagt, er spricht latin1. Mit dieser Einstellung wirst du
keine Unicode-Zeichen außerhalb latin1 vom/zum MySQL-Server bekommen.
Du wirst ohne utf8-tauglichen Client nicht weit kommen.

> collation_connection | latin1_swedish_ci

Das ist die Default-Collation zu latin1. Irrelevant.

> character_set_system | utf8

Das kannst du ohnehin nicht ändern (das Encoding für die Namen von
Datenbank-Objekten).

> character_set_server | utf8
> collation_server | utf8_general_ci
> character_set_database | latin1
> collation_database | latin1_general_ci

Das sind nur Defaults für die Erzeugung neuer Datenbanken/Tabellen.

> Und nun habe ich Dein Script laufenlassen und gemerkt, daß es *keinen*
> Unterschied gibt zwischen

> select hex(tx) from ta;
> select hex(upper(tx)) from ta;
> Und auch nicht bei
> set @al=0xceb1;
> select hex(@al);
> select hex(upper(@al));
> Also weder beim Speichern in der Datenbank noch beim direkten
> "Umrechnen".

Logisch. Da dein Client sagt, er spräche latin1, behandelt MySQL alle
String-Literale von diesem Client als latin1.

> Was übersehe ich denn?

Du denkst nicht mit. Und du liest nicht das Handbuch. Wenn du ein utf8-
Literal schreiben willst, obwohl deine Verbindung auf latin1 gestellt
ist, dann mußt du das explizit hinschreiben. Mal als Denkanstoß:

mysql> show variables like 'char%';
+--------------------------+-----------------------+
| Variable_name | Value |
+--------------------------+-----------------------+
| character_set_client | latin1 |
| character_set_connection | latin1 |
| character_set_results | latin1 |
....

mysql> set @x=0xceb1;
mysql> select @x, hex(@x), hex(upper(@x)), hex(lower(@x));
+------+---------+----------------+----------------+
| @x | hex(@x) | hex(upper(@x)) | hex(lower(@x)) |
+------+---------+----------------+----------------+
| ? | CEB1 | CEB1 | CEB1 |
+------+---------+----------------+----------------+

mysql> set @x=_utf8 0xceb1;
mysql> select @x, hex(@x), hex(upper(@x)), hex(lower(@x));
+------+---------+----------------+----------------+
| @x | hex(@x) | hex(upper(@x)) | hex(lower(@x)) |
+------+---------+----------------+----------------+
| ? | CEB1 | CE91 | CEB1 |
+------+---------+----------------+----------------+

Hier kannst du auch sehen, daß Unicode-Entities außerhalb des gerade
eingestellten Encodings als '?' zurück kommen.


XL

Re: nicht Umlaute, aber fremdsprachige Zeichensätze

am 26.04.2006 14:55:40 von Thomas Rachel

Ralph Stahl wrote:

> character_set_client | latin1
> character_set_connection | latin1
> character_set_database | latin1
> character_set_results | latin1
> character_set_server | utf8
> character_set_system | utf8
> collation_connection | latin1_swedish_ci
> collation_database | latin1_general_ci
> collation_server | utf8_general_ci
>
> (Warum da immer swedish steht, hab ich noch nicht rausgefunden - wohl
> aber, daß ich mit der 5er version nicht der einzige bin, der das sieht).
>
> Und nun habe ich Dein Script laufenlassen und gemerkt, daß es *keinen*
> Unterschied gibt zwischen
>
> select hex(tx) from ta;
> select hex(upper(tx)) from ta;

Stimmt, ich vergaß - ich habe in meiner ~/.my.cnf unter [client] folgende
Zeile stehen:

default-character-set=utf8


>> Dafür darfst Du Dir http://learn.to/quote/ anschauen. ;-)
>> Kleiner Tip: Text oben/Fullquote (TOFU) ist im Usenet nicht gern gesehen.
>
> Ich wollte mich ja nur bedanken :-(.

Und ich helfen.


Thomas

Re: nicht Umlaute, aber fremdsprachige Zeichensätze

am 28.04.2006 20:03:24 von Ralph Stahl

Thomas Rachel schrieb:
> Ralph Stahl wrote:
>
>> character_set_client | latin1
>> character_set_connection | latin1
>> character_set_database | latin1
>> character_set_results | latin1
>> character_set_server | utf8
>> character_set_system | utf8
>> collation_connection | latin1_swedish_ci
>> collation_database | latin1_general_ci
>> collation_server | utf8_general_ci
>>
>> (Warum da immer swedish steht, hab ich noch nicht rausgefunden - wohl
>> aber, daß ich mit der 5er version nicht der einzige bin, der das sieht).
>>
>> Und nun habe ich Dein Script laufenlassen und gemerkt, daß es *keinen*
>> Unterschied gibt zwischen
>>
>> select hex(tx) from ta;
>> select hex(upper(tx)) from ta;
>
> Stimmt, ich vergaß - ich habe in meiner ~/.my.cnf unter [client] folgende
> Zeile stehen:
>
> default-character-set=utf8
>
>
>>> Dafür darfst Du Dir http://learn.to/quote/ anschauen. ;-)
>>> Kleiner Tip: Text oben/Fullquote (TOFU) ist im Usenet nicht gern gesehen.
>> Ich wollte mich ja nur bedanken :-(.
>
> Und ich helfen.

Da werden Sie geholfen! :-)

Nun will es alles so wie ich. Ich habe einfach alle nötigen SETs beim
mysql_connect() gemacht und alles in eine schöne Klasse verpackt, um es
nicht jedes mal machen zu müssen.

Ich bedanke mich bei den Beteiligten!
Ralph