/* features
*
* 素性の番号と意味を隠蔽して管理する
*
* Copyright (C) 2006-2007 TABATA Yusuke
*
*/
/*
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public
License along with this library; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <arpa/inet.h>
#include <anthy/segclass.h>
#include <anthy/feature_set.h>
/* for MW_FEATURE* constants */
#include <anthy/splitter.h>
/* 素性の番号
*
* 0-19 クラス素性
* 30-319(30+SEG_SIZE^2) クラス遷移属性
* 540-579 その他
* 580- (1024個) 付属語の種類
*/
#define CUR_CLASS_BASE 0
#define DEP_TYPE_FEATURE_BASE 20
#define CLASS_TRANS_BASE 30
#define FEATURE_SV 542
#define FEATURE_WEAK 543
#define FEATURE_SUFFIX 544
#define FEATURE_NUM 546
#define FEATURE_CORE1 547
#define FEATURE_HIGH_FREQ 548
#define FEATURE_WEAK_SEQ 549
#define COS_BASE 573
#define DEP_FEATURE_BASE 580
void
anthy_feature_list_init(struct feature_list *fl)
{
fl->nr = 0;
fl->size = NR_EM_FEATURES;
}
void
anthy_feature_list_free(struct feature_list *fl)
{
(void)fl;
}
void
anthy_feature_list_add(struct feature_list *fl, int f)
{
if (fl->nr < NR_EM_FEATURES) {
fl->u.index[fl->nr] = f;
fl->nr++;
}
}
int
anthy_feature_list_nr(const struct feature_list *fl)
{
return fl->nr;
}
int
anthy_feature_list_nth(const struct feature_list *fl, int nth)
{
return fl->u.index[nth];
}
static int
cmp_short(const void *p1, const void *p2)
{
return *((short *)p1) - *((short *)p2);
}
void
anthy_feature_list_sort(struct feature_list *fl)
{
qsort(fl->u.index, fl->nr, sizeof(fl->u.index[0]),
cmp_short);
}
void
anthy_feature_list_set_cur_class(struct feature_list *fl, int cl)
{
anthy_feature_list_add(fl, CUR_CLASS_BASE + cl);
}
void
anthy_feature_list_set_class_trans(struct feature_list *fl, int pc, int cc)
{
anthy_feature_list_add(fl, CLASS_TRANS_BASE + pc * SEG_SIZE + cc);
}
void
anthy_feature_list_set_dep_word(struct feature_list *fl, int h)
{
anthy_feature_list_add(fl, h + DEP_FEATURE_BASE);
}
void
anthy_feature_list_set_dep_class(struct feature_list *fl, int c)
{
anthy_feature_list_add(fl, c + DEP_TYPE_FEATURE_BASE);
}
void
anthy_feature_list_set_noun_cos(struct feature_list *fl, wtype_t wt)
{
int c;
if (anthy_wtype_get_pos(wt) != POS_NOUN) {
return ;
}
c = anthy_wtype_get_cos(wt);
if (c == COS_SUFFIX) {
anthy_feature_list_add(fl, COS_BASE + c);
}
}
void
anthy_feature_list_set_mw_features(struct feature_list *fl, int mask)
{
if (mask & MW_FEATURE_WEAK_CONN) {
anthy_feature_list_add(fl, FEATURE_WEAK);
}
if (mask & MW_FEATURE_SUFFIX) {
anthy_feature_list_add(fl, FEATURE_SUFFIX);
}
if (mask & MW_FEATURE_SV) {
anthy_feature_list_add(fl, FEATURE_SV);
}
if (mask & MW_FEATURE_NUM) {
anthy_feature_list_add(fl, FEATURE_NUM);
}
if (mask & MW_FEATURE_CORE1) {
anthy_feature_list_add(fl, FEATURE_CORE1);
}
if (mask & MW_FEATURE_HIGH_FREQ) {
anthy_feature_list_add(fl, FEATURE_HIGH_FREQ);
}
if (mask & MW_FEATURE_WEAK_SEQ) {
anthy_feature_list_add(fl, FEATURE_WEAK_SEQ);
}
}
void
anthy_feature_list_print(struct feature_list *fl)
{
int i;
printf("features=");
for (i = 0; i < fl->nr; i++) {
if (i) {
printf(",");
}
printf("%d", fl->u.index[i]);
}
printf("\n");
}
static int
compare_line(const void *kp, const void *cp)
{
const int *f = kp;
const struct feature_freq *c = cp;
int i;
for (i = 0; i < NR_EM_FEATURES; i++) {
if (f[i] != (int)ntohl(c->f[i])) {
return f[i] - ntohl(c->f[i]);
}
}
return 0;
}
struct feature_freq *
anthy_find_array_freq(const void *image, int *f, int nr,
struct feature_freq *arg)
{
struct feature_freq *res;
int nr_lines, i;
const int *array = (int *)image;
int n[NR_EM_FEATURES];
if (!image) {
return NULL;
}
/* コピーする */
for (i = 0; i < NR_EM_FEATURES; i++) {
if (i < nr) {
n[i] = f[i];
} else {
n[i] = 0;
}
}
/**/
nr_lines = ntohl(array[1]);
res = bsearch(n, &array[16], nr_lines,
sizeof(struct feature_freq),
compare_line);
if (!res) {
return NULL;
}
for (i = 0; i < NR_EM_FEATURES + 2; i++) {
arg->f[i] = ntohl(res->f[i]);
}
return arg;
}
struct feature_freq *
anthy_find_feature_freq(const void *image,
const struct feature_list *fl,
struct feature_freq *arg)
{
int i, nr;
int f[NR_EM_FEATURES + 2];
/* 配列にコピーする */
nr = anthy_feature_list_nr(fl);
for (i = 0; i < NR_EM_FEATURES + 2; i++) {
if (i < nr) {
f[i] = anthy_feature_list_nth(fl, i);
} else {
f[i] = 0;
}
}
return anthy_find_array_freq(image, f, NR_EM_FEATURES, arg);
}
void
anthy_init_features(void)
{
}
syntax highlighted by Code2HTML, v. 0.9.1