Lindera
Токенизатор lindera выполняет морфологический анализ на основе словаря. Он предназначен для японского и корейского языков, в которых слова не разделяются пробелами, а грамматические маркеры (частицы) присоединяются непосредственно к словам.
Для китайского текста: Хотя lindera поддерживает китайский язык через словарь cc-cedict, мы рекомендуем использовать jieba токенизатор. Jieba специально разработана для сегментации китайских слов и обеспечивает лучшие результаты.
Обзор
Японский и корейский - агглютинативные языки: грамматические маркеры, называемые частицами, присоединяются непосредственно к существительным, образуя многочисленные комбинации. Например:
Язык |
Корневое слово |
+ частица |
= Комбинированная форма |
Значение |
|---|---|---|---|---|
Корейский |
서울 (Сеул) |
에서 |
서울에서 |
в Сеуле |
Японский |
東京 (Токио) |
に |
東京に |
в Токио |
Токенизатор lindera:
Сегментирует текст на отдельные морфемы (слова и частицы)
Помечает каждую лексему информацией о части речи (POS) из словаря
Применяет фильтры для удаления нежелательных лексем (например, частиц, знаков препинания).
Этот двухэтапный процесс - сегментация с последующей фильтрацией на основе POS - позволяет точно контролировать, какие лексемы будут проиндексированы для поиска.
Необходимые условия
Пользователи Milvus 2.6+: Вы можете пропустить этот раздел. Все словари предварительно скомпилированы и включены в официальный релиз.
Для Milvus 2.5.x необходимо скомпилировать Milvus с включенными определенными словарями. Все словари должны быть явно включены во время компиляции.
Чтобы включить определенные словари, включите их в команду компиляции:
make milvus TANTIVY_FEATURES=lindera-ipadic,lindera-ko-dic
Полный список доступных словарей:
Словарь |
Язык |
Описание |
|---|---|---|
lindera-ko-dic |
Корейский |
Морфологический словарь корейского языка(MeCab Ko-dic) |
lindera-ipadic |
Японский |
Стандартный морфологический словарь(MeCab IPADIC) |
линдара-ипадик-неологд |
Японский |
Расширенный словарь с новыми словами и собственными существительными(IPADIC NEologd) |
lindera-unidic |
Японский |
Академический стандартный словарь(UniDic) |
lindera-cc-cedict |
Китайский |
Поддерживаемый сообществом китайско-английский словарь(CC-CEDICT). |
Например, чтобы включить все словари:
make milvus TANTIVY_FEATURES=lindera-ipadic,lindera-ipadic-neologd,lindera-unidic,lindera-ko-dic,lindera-cc-cedict
Конфигурация
Чтобы настроить анализатор, использующий токенизатор lindera, установите tokenizer.type на lindera, выберите словарь с dict_kind и, по желанию, примените фильтры.
analyzer_params = {
"tokenizer": {
"type": "lindera",
"dict_kind": "ko-dic",
"filter": [
{
"kind": "korean_stop_tags",
"tags": ["SP", "SSC", "SSO", "SC", "SE", "SF", "JKS", "JKC", "JKG", "JKO", "JKB", "JKV", "JKQ", "JX", "JC", "UNK", "EP", "ETM"]
}
]
}
}
Map<String, Object> analyzerParams = new HashMap<>();
analyzerParams.put("tokenizer", new HashMap<String, Object>() {{
put("type", "lindera");
put("dict_kind", "ko-dic");
put("filter", Arrays.asList(
new HashMap<String, Object>() {{
put("kind", "korean_stop_tags");
put("tags", Arrays.asList(
"SP", "SSC", "SSO", "SC", "SE", "SF",
"JKS", "JKC", "JKG", "JKO", "JKB", "JKV", "JKQ",
"JX", "JC", "UNK", "EP", "ETM"
));
}}
));
}});
analyzerParams := map[string]interface{}{
"tokenizer": map[string]interface{}{
"type": "lindera",
"dict_kind": "ko-dic",
"filter": []interface{}{
map[string]interface{}{
"kind": "korean_stop_tags",
"tags": []string{
"SP", "SSC", "SSO", "SC", "SE", "SF",
"JKS", "JKC", "JKG", "JKO", "JKB", "JKV", "JKQ",
"JX", "JC", "UNK", "EP", "ETM",
},
},
},
},
}
const analyzer_params = {
"tokenizer": {
"type": "lindera",
"dict_kind": "ko-dic",
"filter": [
{
"kind": "korean_stop_tags",
"tags": ["SP", "SSC", "SSO", "SC", "SE", "SF", "JKS", "JKC", "JKG", "JKO", "JKB", "JKV", "JKQ", "JX", "JC", "UNK", "EP", "ETM"]
}
]
}
};
# restful
Параметр |
Описание |
|---|---|
|
Тип токенизатора. Установлено значение |
|
Словарь, используемый для определения лексики. Возможные значения:
|
|
Список фильтров уровня токенизатора для применения после сегментации. Каждый фильтр - это объект с:
|
Определив analyzer_params, вы можете применить их к полю VARCHAR при определении схемы коллекции. Это позволит Milvus обрабатывать текст в этом поле с помощью указанного анализатора для эффективной токенизации и фильтрации. Подробнее см. в разделе Пример использования.
Примеры
Прежде чем применять конфигурацию анализатора к схеме коллекции, проверьте его работу с помощью метода run_analyzer.
Корейский пример
from pymilvus import MilvusClient
client = MilvusClient(uri="http://localhost:19530")
analyzer_params = {
"tokenizer": {
"type": "lindera",
"dict_kind": "ko-dic",
"filter": [
{
"kind": "korean_stop_tags",
"tags": ["SP", "SSC", "SSO", "SC", "SE", "SF", "JKS", "JKC", "JKG", "JKO", "JKB", "JKV", "JKQ", "JX", "JC", "UNK", "EP", "ETM"]
}
]
}
}
# Sample Korean text: "서울에서 맛있는 음식을 먹었습니다" (I ate delicious food in Seoul)
sample_text = "서울에서 맛있는 음식을 먹었습니다"
result = client.run_analyzer(sample_text, analyzer_params)
print("Analyzer output:", result)
import io.milvus.v2.client.ConnectConfig;
import io.milvus.v2.client.MilvusClientV2;
import io.milvus.v2.service.vector.request.RunAnalyzerReq;
import io.milvus.v2.service.vector.response.RunAnalyzerResp;
ConnectConfig config = ConnectConfig.builder()
.uri("http://localhost:19530")
.build();
MilvusClientV2 client = new MilvusClientV2(config);
Map<String, Object> analyzerParams = new HashMap<>();
analyzerParams.put("tokenizer", new HashMap<String, Object>() {{
put("type", "lindera");
put("dict_kind", "ko-dic");
put("filter", Arrays.asList(
new HashMap<String, Object>() {{
put("kind", "korean_stop_tags");
put("tags", Arrays.asList(
"SP", "SSC", "SSO", "SC", "SE", "SF",
"JKS", "JKC", "JKG", "JKO", "JKB", "JKV", "JKQ",
"JX", "JC", "UNK", "EP", "ETM"
));
}}
));
}});
List<String> texts = new ArrayList<>();
texts.add("서울에서 맛있는 음식을 먹었습니다");
RunAnalyzerResp resp = client.runAnalyzer(RunAnalyzerReq.builder()
.texts(texts)
.analyzerParams(analyzerParams)
.build());
List<RunAnalyzerResp.AnalyzerResult> results = resp.getResults();
import (
"context"
"encoding/json"
"fmt"
"github.com/milvus-io/milvus/client/v2/milvusclient"
)
client, err := milvusclient.New(ctx, &milvusclient.ClientConfig{
Address: "localhost:19530",
APIKey: "root:Milvus",
})
if err != nil {
fmt.Println(err.Error())
// handle error
}
analyzerParams := map[string]interface{}{
"tokenizer": map[string]interface{}{
"type": "lindera",
"dict_kind": "ko-dic",
"filter": []interface{}{
map[string]interface{}{
"kind": "korean_stop_tags",
"tags": []string{
"SP", "SSC", "SSO", "SC", "SE", "SF",
"JKS", "JKC", "JKG", "JKO", "JKB", "JKV", "JKQ",
"JX", "JC", "UNK", "EP", "ETM",
},
},
},
},
}
bs, _ := json.Marshal(analyzerParams)
texts := []string{"서울에서 맛있는 음식을 먹었습니다"}
option := milvusclient.NewRunAnalyzerOption(texts).
WithAnalyzerParams(string(bs))
result, err := client.RunAnalyzer(ctx, option)
if err != nil {
fmt.Println(err.Error())
// handle error
}
import { MilvusClient } from "@zilliz/milvus2-sdk-node";
const client = new MilvusClient({
uri: "http://localhost:19530",
});
const analyzer_params = {
tokenizer: {
type: "lindera",
dict_kind: "ko-dic",
filter: [
{
kind: "korean_stop_tags",
tags: [
"SP",
"SSC",
"SSO",
"SC",
"SE",
"SF",
"JKS",
"JKC",
"JKG",
"JKO",
"JKB",
"JKV",
"JKQ",
"JX",
"JC",
"UNK",
"EP",
"ETM",
],
},
],
},
};
const sample_text = "서울에서 맛있는 음식을 먹었습니다";
const result = await client.run_analyzer(sample_text, analyzer_params);
console.log("Analyzer output:", result);
# restful
Ожидаемый результат:
['서울', '맛있', '음식', '먹', '습니다']
Если бы не было метода korean_stop_tags, то в результатах были бы частицы типа 에서 (in), 는 (маркер темы) и 을 (маркер объекта), которые обычно не используются для поиска.
Японский пример
from pymilvus import MilvusClient
client = MilvusClient(uri="http://localhost:19530")
analyzer_params = {
"tokenizer": {
"type": "lindera",
"dict_kind": "ipadic",
"filter": [
{
"kind": "japanese_stop_tags",
"tags": ["接続詞", "助詞,格助詞", "助詞,格助詞,一般", "助詞,格助詞,引用", "助詞,格助詞,連語", "助詞,係助詞", "助詞,終助詞", "助詞,接続助詞", "助詞,特殊", "助詞,副助詞", "助詞,副助詞/並立助詞/終助詞", "助詞,連体化", "助詞,副詞化", "助詞,並立助詞", "助動詞", "記号,一般", "記号,読点", "記号,句点", "記号,空白", "記号,括弧閉", "記号,括弧開", "その他,間投", "フィラー", "非言語音"]
}
]
}
}
# Sample Japanese text: "東京スカイツリーの最寄り駅はとうきょうスカイツリー駅です"
sample_text = "東京スカイツリーの最寄り駅はとうきょうスカイツリー駅です"
result = client.run_analyzer(sample_text, analyzer_params)
print("Analyzer output:", result)
// java
// go
import { MilvusClient } from "@zilliz/milvus2-sdk-node";
const client = new MilvusClient({
uri: "http://localhost:19530",
});
const analyzer_params = {
"tokenizer": {
"type": "lindera",
"dict_kind": "ipadic",
"filter": [
{
"kind": "japanese_stop_tags",
"tags": ["接続詞", "助詞,格助詞", "助詞,格助詞,一般", "助詞,格助詞,引用", "助詞,格助詞,連語", "助詞,係助詞", "助詞,終助詞", "助詞,接続助詞", "助詞,特殊", "助詞,副助詞", "助詞,副助詞/並立助詞/終助詞", "助詞,連体化", "助詞,副詞化", "助詞,並立助詞", "助動詞", "記号,一般", "記号,読点", "記号,句点", "記号,空白", "記号,括弧閉", "記号,括弧開", "その他,間投", "フィラー", "非言語音"]
}
]
}
}
// Sample Japanese text: "東京スカイツリーの最寄り駅はとうきょうスカイツリー駅です"
const sample_text = "東京スカイツリーの最寄り駅はとうきょうスカイツリー駅です"
const result = await client.run_analyzer(sample_text, analyzer_params);
console.log("Analyzer output:", result);
# restful
Ожидаемый результат:
['東京', 'スカイ', 'ツリー', '最寄り駅', 'とう', 'きょう', 'スカイ', 'ツリー', '駅']
Без japanese_stop_tags результат будет включать такие частицы, как の (притяжательный), は (маркер темы) и です (копула).