Skip to content

Instantly share code, notes, and snippets.

@nazoking
Last active November 19, 2019 09:01
Show Gist options
  • Select an option

  • Save nazoking/e9a7fd48023baf06ccd8aba6baf8fae6 to your computer and use it in GitHub Desktop.

Select an option

Save nazoking/e9a7fd48023baf06ccd8aba6baf8fae6 to your computer and use it in GitHub Desktop.

http://www.chokkan.org/software/crfsuite/manual.html

CRFsuite - ドキュメンテーション

目次

トレーニング/タグ付けデータの形式

このセクションでは、CRFsuiteがトレーニングおよびタグ付けに使用するデータ形式について説明します。 データは一連の項目シーケンスで構成され、各項目シーケンスは連続する行で表され、空の行で終わります。 アイテムシーケンスは、その特性(ラベルおよび属性)がラインで記述された一連のアイテムで構成されます。 項目行はラベルで始まり、属性はTAB(\t)文字で区切られます。

これはトレーニングデータの例です(CoNLL 2000チャンク共有タスクから取得)。

http://www.chokkan.org/software/crfsuite/data_sample.png 図1. CRFsuiteのサンプルデータ

この例には、4つのアイテムシーケンスが含まれています(最後のものは部分的に示されています)。第1のシーケンスの第1の項目は、ラベル B-NP で注釈され、w[0]=Anw[1]=APpos[0]=DTpos[1]= NNP__ BOS__ です。この例のラベルと属性は、特定の命名規則(フィーチャデザイン)に従います。B-NP は現在のトークンが名詞句の始まりであることを示し、w[0]=Anは、現在のアイテムの表面形態が「An」であることを示し、pos[1]=NNP は次のトークンが固有名詞であることを示し、 __ BOS__ は現在のアイテムがシーケンスの最初のアイテムであることを示します。しかし、CRFsuiteはラベルや属性の命名規則や機能設計には関心がありませんが、単なる文字列として扱います。 CRFsuiteは、ラベルと属性の意味を知らなくても、属性とラベルの関連性(特徴の重み)を学習します(例えば、現在のアイテムが属性 pos[0]=DT を有する場合、意味のわからないラベル B-NP を有する可能性が高い)。つまり、ラベルや属性名をデータセットに書き込むだけで任意の機能を設計して使用することができます。

属性は、コロン文字()で区切られたスケーリング値を持つことができます。正式には、特徴の影響量は、対応する属性のスケーリング値にフィーチャウェイトを乗じて決定されます。大まかに言えば、属性のスケーリング値は、属性の出現頻度と同様の効果を持ちますが、小数点または桁違いにすることもできます。スケーリング値が大きいと、トレーニングでオーバーフロー(レンジエラー)が発生する可能性があることに注意してください。コロン文字はデータセットで特別な役割を持つため、CRFsuiteはエスケープシーケンスを使用します。 「\:」および「\\」は、それぞれ属性名の「」および「\」を表します。属性値が省略された場合(コロン文字なし)、CRFsuiteはスケーリング値を 1 とみなします。たとえば、これらの3つの項目は、属性とスケーリング値の点で同じです。

B-NP    w[1..4]=a:2 w[1..4]=man w[1..4]=eats

B-NP    w[1..4]=a w[1..4]=a w[1..4]=man w[1..4]=eats

B-NP    w[1..4]=a:2.0 w[1..4]=man:1.0 w[1..4]=eats:1.0

タグ付けのデータ形式は、学習用のデータ形式とまったく同じですが、タグ付けデータ内のラベルは空にすることができます(ただし、省略することはできません)。 タグ付きの場合、CRFsuiteは入力データ内のラベルを無視するか、または予測のパフォーマンスを測定するためにそれらを使用します。

これは、データ形式を表すBNF記法です。

<line>           ::= <item> | <eos>
<item>           ::= <label> ('\t' <attribute>)+ <br>
<eos>            ::= <br>
<label>          ::= <string>
<attribute>      ::= <name> | <name> ':' <scaling>
<name>           ::= (<letter> | "\:" | "\\")+
<scaling>        ::= <numeric>
<br>             ::= '\n'

インストール

バイナリディストリビューションを使用する

CRFsuiteをインストールする最も簡単な方法は、バイナリ配布を使用することです。現在、Win32およびLinux(Intel 32ビットおよび64ビットアーキテクチャ)のバイナリが配布されています。

ソース配布物からバイナリをビルドする

CRFsuite 0.5以降、ソースパッケージにはlibLBFGSの部分が含まれなくなりました。 CRFsuiteをビルドするには、まずlibLBFGSをダウンロードしてビルドする必要があります。

Windows環境では、libLBFGSのVisual Studioソリューションファイル(lbfgs.sln)を開いてビルドします。ソリューションファイルは、ReleaseまたはDebugディレクトリにスタティックリンクライブラリlbfgs.lib(リリースビルド)またはlbfgs_debug.lib(デバッグビルド)をビルドします。 CRFsuiteのソリューションファイル(crfsuite.sln)は、libLBFGSのヘッダファイルとライブラリファイルがwin32 / lbfgsディレクトリに存在することを前提としているため、このディレクトリを作成し、lbfgs.h、lbfgs.lib、および/またはlbfgs_debug.libをディレクトリにコピーします。次に、ソリューションファイル(crfsuite.sln)を開いてビルドします。

Linux環境では、libLBFGSのソースパッケージをダウンロードしてビルドします。ご使用のオペレーティングシステムにlibLBFGSをインストールしない場合は、configureスクリプトに " - prefix"オプションを指定してください。この例では、ホームディレクトリ($ HOME)の下のlocalディレクトリにlibLBFGSをインストールします。

$ ./configure --prefix=$HOME/local
$ make
$ make install

CRFsuiteを作成する準備が整いました。 libLFGSを別のディレクトリにインストールしている場合は、 "--with-liblbfgs"オプションの引数にディレクトリを指定してください。

$ ./configure --prefix=$HOME/local --with-liblbfgs=$HOME/local
$ make
$ make install

使用法

CRFsuiteユーティリティは、最初のコマンドライン引数がコマンド名であることを想定しています。

  • 学ぶ
    • トレーニングセットからCRFモデルをトレーニングする。
  • タグ
    • CRFモデルを用いてタグ配列をタグする。
  • ダンプ
    • CRFモデルをプレーンテキスト形式でダンプします。

コマンドライン構文を表示するには、-h(--help)オプションを使用します。

$ crfsuite -h
CRFSuite 0.12  Copyright (c) 2007-2011 Naoaki Okazaki

USAGE: crfsuite <COMMAND> [OPTIONS]
    COMMAND     Command name to specify the processing
    OPTIONS     Arguments for the command (optional; command-specific)

COMMAND:
    learn       Obtain a model from a training set of instances
    tag         Assign suitable labels to given instances by using a model
    dump        Output a model in a plain-text format

For the usage of each command, specify -h option in the command argument.

トレーニング

トレーニングセットからCRFモデルをトレーニングするには、次のコマンドを入力します。

$ crfsuite learn [OPTIONS] [DATA]

引数DATAが省略された場合、または ' - 'の場合、このユーティリティはSTDINからトレーニングデータを読み込みます。 learnコマンドの使用法を表示するには、-h(--help)オプションを指定します。

$ crfsuite learn -h
CRFSuite 0.12  Copyright (c) 2007-2011 Naoaki Okazaki

USAGE: crfsuite learn [OPTIONS] [DATA1] [DATA2] ...
Trains a model using training data set(s).

  DATA    file(s) corresponding to data set(s) for training; if multiple N files
          are specified, this utility assigns a group number (1...N) to the
          instances in each file; if a file name is '-', the utility reads a
          data set from STDIN

OPTIONS:
  -t, --type=TYPE       specify a graphical model (DEFAULT='1d'):
                        (this option is reserved for the future use)
      1d                    1st-order Markov CRF with state and transition
                            features; transition features are not conditioned
                            on observations
  -a, --algorithm=NAME  specify a training algorithm (DEFAULT='lbfgs')
      lbfgs                 L-BFGS with L1/L2 regularization
      l2sgd                 SGD with L2-regularization
      ap                    Averaged Perceptron
      pa                    Passive Aggressive
      arow                  Adaptive Regularization of Weights (AROW)
  -p, --set=NAME=VALUE  set the algorithm-specific parameter NAME to VALUE;
                        use '-H' or '--help-parameters' with the algorithm name
                        specified by '-a' or '--algorithm' and the graphical
                        model specified by '-t' or '--type' to see the list of
                        algorithm-specific parameters
  -m, --model=FILE      store the model to FILE (DEFAULT=''); if the value is
                        empty, this utility does not store the model
  -g, --split=N         split the instances into N groups; this option is
                        useful for holdout evaluation and cross validation
  -e, --holdout=M       use the M-th data for holdout evaluation and the rest
                        for training
  -x, --cross-validate  repeat holdout evaluations for #i in {1, ..., N} groups
                        (N-fold cross validation)
  -l, --log-to-file     write the training log to a file instead of to STDOUT;
                        The filename is determined automatically by the training
                        algorithm, parameters, and source files
  -L, --logbase=BASE    set the base name for a log file (used with -l option)
  -h, --help            show the usage of this command and exit
  -H, --help-parameters show the help message of algorithm-specific parameters;
                        specify an algorithm with '-a' or '--algorithm' option,
                        and specify a graphical model with '-t' or '--type' option

トレーニングには以下のオプションがあります。

  • -t、--type=TYPE フィーチャ生成に使用するグラフィカルモデルを指定します。 デフォルト値は "1d"です。
    • 1d 状態と遷移の特徴を持つ1次マルコフCRF(ダイアド機能)。 状態の特徴は属性とラベルの組み合わせを条件とし、遷移特徴はラベルのバイグラムに条件付けされます。
  • -a、--algorithm=NAME トレーニングアルゴリズムを指定します。 デフォルト値は "lbfgs"です。
    • lbfgs L-BFGS法による勾配降下
    • l2sgd L2正規化項を伴う確率的勾配降下
    • ap 平均パーセプトロン
    • PA パッシブアグレッシブ(PA)
    • arow 重みベクトル(AROW)の適応正規化
  • -p、--param=NAME=VALUE トレーニングのパラメータを設定します。 CRFsuiteは、パラメータ(NAME)をVALUEに設定します。利用可能なパラメータは、選択されたグラフィカルモデルおよびトレーニングアルゴリズムに依存する。使用可能なパラメータのヘルプメッセージを表示するには、 '-a'または '--algorithm'で指定されたアルゴリズム名と '-t'または '--algorithm'で指定されたグラフィカルモデルで '-H'または '--help- - タイプ'。
  • -m、--model=MODEL 訓練されたモデルをMODELファイルに格納します。デフォルト値は ""(空)です。 MODELが空の場合、CRFsuiteはモデルをファイルに保存しません。
  • -g、--split=N インスタンスをN個のグループに分割し、{1、...、N}の番号を各グループに割り当てます。このオプションは主にN倍のクロスバリデーション(-xオプション付き)を実行するために使用されます。デフォルトでは、CRFsuiteは入力データをグループに分割しません。
  • -e、--holdout=M 保留評価にはグループ番号Mのインスタンスを使用します。 CRFsuiteは、グループ番号Mのインスタンスをトレーニングに使用しません。デフォルトでは、CRFsuiteは保留評価を実行しません。
  • -x、--cross-validate N倍交差検証を実行します。 -gオプションを使用して分割数を指定します。デフォルトでは、CRFsuiteはクロスバリデーションを実行しません。
  • -l、--log-to-file トレーニングのログメッセージをファイルに書き出します。ファイル名は、コマンドライン引数(トレーニングアルゴリズム、グラフィカルモデル、パラメータ、ソースファイルなど)から自動的に決定されます。デフォルトでは、CRFsuiteはログメッセージをSTDOUTに書き込みます。
  • -L、--logbase=BASE ログファイルのベース名を指定します(-lオプションとともに使用します)。 デフォルトでは、ベース名は "log.crfsuite"です。
  • -h、--help このコマンドの使用法を表示して終了します。
  • -H、--help-parameters パラメータとその説明のリストを表示します。 -tおよび-aオプションを使用して、グラフィカルモデルとトレーニングアルゴリズムをそれぞれ指定します。
  • -p、--param=NAME=VALUE トレーニングのパラメータを設定します。 CRFsuiteは、パラメータ(NAME)をVALUEに設定します。 パラメータとその説明のリストを表示するには、-H(--help-parameters)オプションを使用します。

トレーニングのためのCRFsuiteコマンドラインのいくつかの例を以下に示します。

train.txtのCRFモデルをデフォルトのパラメータでトレーニングし、モデルをCRF.modelに保存します。

$ crfsuite learn -m CRF.model train.txt

STDINのCRFモデルをデフォルトのパラメータでトレーニングします。

$ cat train.txt | crfsuite learn -

train.txt(グループ#1)からCRFモデルをトレーニングします。 訓練中に、ホールドアウトデータtest.txt(グループ#2)でモデルをテストします。

$ crfsuite learn -e2 train.txt test.txt

トレーニングデータtrain.txtで10倍のクロスバリデーションを実行します。 ログ出力はlog.crfsuite_lbfgsに格納されます(ログファイルの名前は、トレーニングパラメータによって異なる場合があります)。

$ crfsuite learn -g10 -x -l train.txt

グラフィカルモデル

1d:一次マルコフCRFダイアド機能付き

状態と遷移の特徴を持つ1次マルコフCRF(ダイアド機能)。状態の特徴は属性とラベルの組み合わせを条件とし、遷移特徴はラベルのバイグラムに条件付けされます。

  • feature.minfreq=VALUE フィーチャの発生頻度のカットオフしきい値。 CRFsuiteは、訓練データ中の出現頻度がVALUEより大きくない特徴を無視する。デフォルト値は0(つまり、カットオフなし)です。
  • feature.possible_states=BOOL CRFsuiteが訓練データ内に存在しない状態特徴(すなわち、負の状態の特徴)を生成するかどうかを指定する。 BOOLを1に設定すると、CRFsuiteは属性とラベルの間に考えられるすべての組み合わせを関連付ける状態機能を生成します。属性とラベルの数をそれぞれAとLとすると、この関数は(A * L)個の特徴を生成します。この機能を有効にすると、CRFモデルで項目が参照ラベルに予測されない状態を知ることができるため、ラベル付けの精度が向上する可能性があります。しかし、この機能は、フィーチャの数を増やし、トレーニングプロセスを大幅に遅くする可能性があります。この機能はデフォルトで無効になっています。
  • feature.possible_transitions=BOOL CRFsuiteが訓練データ内にさえも存在しない遷移特徴(すなわち、負の遷移特徴)を生成するかどうかを指定する。 BOOLを1に設定すると、CRFsuiteはすべての可能なラベルペアを関連付ける遷移機能を生成します。訓練データのラベルの数がLであるとすると、この関数は(L * L)の遷移特徴を生成する。この機能はデフォルトで無効になっています。

CRFsuiteコマンドラインの例をいくつか紹介します。

2回未満の機能はトレーニングに使用されません。

$ crfsuite learn -m CRF.model -p feature.minfreq = 2 train.txt

負の状態と遷移のフィーチャ(別名、密なフィーチャセット)を生成します。

$ crfsuite learn -m CRF.model -p feature.possible_states=1 -p feature.possible_transitions=1 train.txt

トレーニングアルゴリズム

lbfgs:限定されたメモリBroyden-Fletcher-Goldfarb-Shanno(L-BFGS)メソッド

制限された記憶Broyden-Fletcher-Goldfarb-Shanno(L-BFGS)法を用いてL1および/またはL2正規化項を用いて訓練データの尤度の対数を最大化する。 L1正則化項の非ゼロ係数が指定されると、アルゴリズムは、正則 - 限定的メモリ - 準ニュートン(OWL-QN)法に切り替わる。 実際には、このアルゴリズムはトレーニングプロセスの開始時にフィーチャウェイトを非常にゆっくりと改善しますが、最終的に最適なフィーチャウェイトにすばやく収束します。

  • c1=VALUE L1正則化の係数。ゼロ以外の値を指定すると、CRFsuiteはOrthant-Wise Limited-Memory Quasi-Newton(OWL-QN)メソッドに切り替わります。デフォルト値はゼロです(L1正規化なし)。
  • c2=VALUE L2正則化の係数。デフォルト値は1です。
  • max_iterations=NUM L-BFGS最適化の最大反復回数。反復回数がこの値を超えると、L-BFGSルーチンは終了します。デフォルト値は、マシンの整数の最大値(INT_MAX)に設定されています。
  • num_memories=NUM L-BFGSが逆ヘッセ行列を近似するために使用する制限されたメモリの数。デフォルト値は6です。
  • epsilon=VALUE コンバージェンスの条件を決定するイプシロンパラメータ。デフォルト値は1e-5です。
  • stop=NUM 停止基準をテストするための反復の継続時間。デフォルト値は10です。
  • delta=VALUE 停止基準のしきい値。 L-BFGS反復は、最後の$ {stop}反復に対する対数尤度の改善がこの閾値以下であるときに停止する。デフォルト値は1e-5です。
  • linesearch=STRING L-BFGSアルゴリズムで使用される線探索法。利用可能なメソッドは、 "MoreThuente"(MoreとThuenteによって提案されたMoreThuenteメソッド)、 "Backtracking"(通常のWolfe条件でのバックトラッキングメソッド)、 "StrongBacktracking"(強力なWolfe条件でのバックトラッキングメソッド)です。デフォルトの方法は "MoreThuente"です。
  • max_linesearch=NUM ライン検索アルゴリズムの試行回数の最大値。デフォルト値は20です。

L-BFGSトレーニングのコマンドラインのいくつかの例を以下に示します。

L2正則化(c1 = 0、c2 = 1.0)でモデルを訓練する。

$ crfsuite learn -m CRF.model -a lbfgs -p c2=1 train.txt

L1正則化(c1 = 1.0、c2 = 0)でモデルを訓練する。

$ crfsuite learn -m CRF.model -a lbfgs -p c1=1 -p c2=0 train.txt

L1とL2の正則化(c1 = 1.0、c2 = 1.0)でモデルを訓練する。

$ crfsuite learn -m CRF.model -a lbfgs -p c1=1 -p c2=1 train.txt

l2sgd:L2正則化を伴う確率的勾配(SGD)

バッチサイズ1の確率勾配降下(SGD)を使用して、L2正則化項を用いて訓練データの尤度の対数を最大化する。このアルゴリズムは通常、最適な特徴重みに非常に迅速に近づくが、最後に遅い収束を示す。

  • c2=VALUE L2正則化の係数。デフォルト値は1です。
  • max_iterations=NUM SGD最適化の最大反復回数(エポック)。最適化ルーチンは、繰り返し回数がこの値を超えると終了します。デフォルト値は1000です。
  • period=NUM 停止基準をテストするための反復の継続時間。デフォルト値は10です。
  • delta=VALUE 停止基準のしきい値。最後の$ {period}反復での対数尤度の改善がこの閾値以下であるとき、最適化プロセスは停止する。デフォルト値は1e-5です。
  • calibration.eta=VALUE 校正に使用される学習率(η)の初期値。デフォルト値は0.1です。
  • calibration.rate=VALUE 較正のための学習率の増減率。デフォルト値は2です。
  • calibration.samples=NUM 較正に使用されるインスタンスの数。較正ルーチンは、VALUEより大きくないインスタンスをランダムに選択する。デフォルト値は1000です。
  • calibration.candidates=NUM 学習率の候補者の数。較正ルーチンは、対数尤度を高めることができる学習率の候補NUMを見つけた後に終了する。デフォルト値は10です。
  • calibration.max_trials=NUM 校正の学習率の最大試行回数。較正ルーチンは、学習率の候補値NUMを試した後に終了する。デフォルト値は20です。

次に、SGDトレーニングのコマンドラインの例を示します。

L2正則化(c2=1.0)でモデルを訓練する。

$ crfsuite learn -m CRF.model -a l2sgd -p c2=1 train.txt

ap:平均パーセプトロン

現在のモデルパラメータがアイテムシーケンスを正しく予測できない場合、このアルゴリズムはパーセプトロン更新をモデルに適用します。このアルゴリズムは、トレーニングプロセスのすべての更新でフィーチャウェイトの平均をとる。アルゴリズムはトレーニングのスピードの点で最も高速です。アルゴリズムは非常に簡単ですが、高い予測性能を示します。実際には、反復の最大回数を指定することによってトレーニングプロセスを停止する必要があります。反復の最大回数は、開発セットで調整する必要があります。

  • max_iterations=NUM 反復の最大回数(エポック)。最適化ルーチンは、繰り返し回数がこの値を超えると終了します。デフォルト値は100です。
  • epsilon=VALUE コンバージェンスの条件を決定するイプシロンパラメータ。モデルによって予測された不正確なラベルの比率がVALUEより大きくない場合、最適化ルーチンは終了する。デフォルト値は1e-5です。

ここでは、Averaged Perceptronのコマンドラインの例を示します。

10回の反復でモデルを訓練する。

$ crfsuite learn -m CRF.model -a ap -p max_iterations = 10 train.txt
pa:パッシブアグレッシブ

トレーニングデータ中のアイテムシーケンス(x、y)が与えられた場合、アルゴリズムは損失を計算する。ここで、s(x、y) (y ')はビタビ・ラベル・シーケンスのスコアであり、s(x、y)はトレーニング・データのラベル・シーケンスのスコアであり、d(y'、y)はビタビ・ラベル・シーケンス)および参照ラベル配列(y)を含む。アイテムに負でない損失がない場合、アルゴリズムは損失に基づいてモデルを更新します。

  • type=NUM フィーチャウェイトを更新するための戦略:スラック変数なしのPA(0)、PAタイプI(1)、またはPAタイプII(2)。デフォルト値は1です。
  • c=VALUE アグレッシブ性パラメータ(PA-IおよびPA-IIにのみ使用されます)。このパラメータは目的関数へのスラック項の影響を制御します。デフォルト値は1です。
  • error_sensitive=BOOL このパラメータが真(非ゼロ)である場合、最適化ルーチンは目的関数に、モデルによって予測された不正確なラベルの数の平方根を含む。デフォルト値は1(真​​)です。
  • averaging=BOOL このパラメータが真(非ゼロ)である場合、最適化ルーチンは、トレーニングプロセスにおけるすべての更新における特徴重みの平均を計算する(Averaged Perceptronと同様)。デフォルト値は1(真​​)です。
  • max_iterations=NUM 反復の最大回数(エポック)。最適化ルーチンは、繰り返し回数がこの値を超えると終了します。デフォルト値は100です。
  • epsilon=VALUE コンバージェンスの条件を決定するイプシロンパラメータ。平均損失がVALUEより大きくない場合、最適化ルーチンは終了する。デフォルト値は1e-5です。

arow:ウェイトベクトル(AROW)の適応正規化

トレーニングデータ内のアイテムシーケンス(x、y)が与えられた場合、アルゴリズムはロスを計算する。s(x、y ')はビタビラベルのスコアである s(x、y)は、トレーニングデータのラベルシーケンスのスコアである。

  • variance=VALUE すべての特徴量の初期分散。 このアルゴリズムは、平均0と分散VALUEを持つ多変量ガウス分布として特徴量のベクトルを初期化します。 デフォルト値は1です。
  • gamma=VALUE 損失関数と特徴量の変化との間のトレードオフ。 デフォルト値は1です。
  • max_iterations=NUM 反復の最大回数(エポック)。 最適化ルーチンは、繰り返し回数がこの値を超えると終了します。 デフォルト値は100です。
  • epsilon=VALUE コンバージェンスの条件を決定するイプシロンパラメータ。 平均損失がVALUEより大きくない場合、最適化ルーチンは終了する。 デフォルト値は1e-5です。

タグ付け

CRFモデルを使用してデータにタグを付けるには、次のコマンドを入力します。

$ crfsuite tag [OPTIONS] [DATA]

引数DATAが省略された場合、または ' - 'の場合、CRFsuiteはSTDINからデータを読み取ります。タグコマンドの使用法を表示するには、-h(--help)オプションを指定します。

$ crfsuite tag -h
CRFSuite 0.12  Copyright (c) 2007-2011 Naoaki Okazaki

USAGE: crfsuite tag [OPTIONS] [DATA]
Assign suitable labels to the instances in the data set given by a file (DATA).
If the argument DATA is omitted or '-', this utility reads a data from STDIN.
Evaluate the performance of the model on labeled instances (with -t option).

OPTIONS:
    -m, --model=MODEL   Read a model from a file (MODEL)
    -t, --test          Report the performance of the model on the data
    -r, --reference     Output the reference labels in the input data
    -p, --probability   Output the probability of the label sequences
    -i, --marginal      Output the marginal probabilities of items
    -q, --quiet         Suppress tagging results (useful for test mode)
    -h, --help          Show the usage of this command and exit

タグ付けには次のオプションがあります。

  • -m、--model=MODEL CRFsuiteがCRFモデルを読み込むファイル名。
  • -t、--test 入力データにラベルが付けられていると仮定して、CRFモデルのパフォーマンス(精度、精度、リコール、f1尺度)を評価します。この機能はデフォルトで無効になっています。
  • -r、--reference 入力ラベルがラベル付けされていると仮定して、予測ラベルと並列に参照ラベルを出力します。この機能はデフォルトで無効になっています。
  • -p、--probability モデルによって予測されたラベル配列の確率を出力する。この機能を有効にすると、ラベルシーケンスは "@probability \ tx.xxxx"という行で始まります。 "x.xxxx"はシーケンスの確率を表し、 "\ t"はTAB文字を表します。この機能はデフォルトで無効になっています。
  • -i、--marginal ラベルの限界確率を出力する。この機能を有効にすると、予測される各ラベルの後ろに「:x.xxxx」が続きます。「x.xxxx」はラベルの確率を表します。この機能はデフォルトで無効になっています。
  • -q、--quiet タグ付きラベルの出力を抑制します。この関数は、-tオプションを使用してCRFモデルを評価する場合に便利です。
  • -h、--help このコマンドの使用法を表示して終了します。

タグ付けのためのCRFsuiteコマンドラインのいくつかの例を以下に示します。

CRFモデルCRF.modelを使用してデータtest.txtにタグを付ける

$ crfsuite tag -m CRF.model test.txt

ラベリングされたデータtest.txt上のCRFモデルCRF.modelを評価する。

$ crfsuite tag -m CRF.model -qt test.txt

モデルダンプ

CRFモデルをプレーンテキスト形式でダンプするには、次のコマンドを入力します。

$ crfsuite dump <MODEL>

http://www.chokkan.org/software/crfsuite/tutorial.html

CRFsuite - Chunkingタスクに関するチュートリアル

タスクの説明

テキストチャンクは、テキストを構文的に相関する単語の部分に分割します。 例えば、He reckons the current account deficit will narrow to only # 1.8 billion in September. との文章は、次のように分けることができます。

[NP He ] [VP reckons ] [NP the current account deficit ] [VP will narrow ] [PP to ] [NP only # 1.8 billion ] [PP in ] [NP September ] .

この例では、NPは名詞句、VPは動詞句、PPは前置詞句を表します。 このタスクは、テキスト内の一連のトークンに一連のラベルが割り当てられたシーケンシャルラベリングタスクとして形式化されます。 チャンク(トークンのスパン)をラベルで表現するために、IOB2表記を使用することがよくあります。 IOB2記法を使用すると、チャンクNPは、チャンク(B-NP)の開始およびチャンク(I-NP)の内部によって表される。 チャンクに属さないトークンはOラベルで表されます。

B-NP He
B-VP reckons
B-NP the
I-NP current
I-NP account
I-NP deficit
B-VP will
I-VP narrow
B-PP to
B-NP only
I-NP #
I-NP 1.8
I-NP billion
B-PP in
B-NP September
O    .

このチュートリアルの目的は、CRFsuiteを使用して、特定の文(トークンのシーケンス)のチャンクラベルを予測するモデルを構築することです。

データのトレーニングとテスト

このチュートリアルでは、CoNLL 2000共有タスクによって配布されたトレーニングおよびテストデータを使用します。 このチュートリアルで必要なスクリプトは、CRFsuiteディストリビューションのexampleディレクトリにあります。 まず、現在のディレクトリをexampleディレクトリに移動し、Webサイトからトレーニングとテストのデータをダウンロードします。

$ cd example
$ wget http://www.cnts.ua.ac.be/conll2000/chunking/train.txt.gz
$ wget http://www.cnts.ua.ac.be/conll2000/chunking/test.txt.gz
$ less train.txt.gz
... (snip) ...

London JJ B-NP
shares NNS I-NP
closed VBD B-VP
moderately RB B-ADVP
lower JJR I-ADVP
in IN B-PP
thin JJ B-NP
trading NN I-NP
. . O

At IN B-PP
Tokyo NNP B-NP
, , O
the DT B-NP
Nikkei NNP I-NP
index NN I-NP
of IN B-PP
225 CD B-NP
selected VBN I-NP
issues NNS I-NP
was VBD B-VP
up IN B-ADVP
112.16 CD B-NP
points NNS I-NP
to TO B-PP
35486.38 CD B-NP
. . O

... (snip) ...

データは、一連の単語(例えば、「ロンドン」、「株式」)、品詞タグ(例えば、「JJ」、「NNS」)を含む一連の文章 スペース文字で区切られたチャンクラベル(例えば、「B-NP」、「I-NP」)を含む。 このチュートリアルでは、一連の単語と品詞コードが与えられている一連のチャンクラベルを割り当てるCRFモデルを作成します。 データセットの詳細については、CoNLL 2000共有タスクWebサイトを参照してください。

特徴(属性)生成

次のステップでは、トレーニングとテストのデータを事前処理して、データ内の単語(項目)の特性を表す属性を抽出します。 CRFsuiteは内部的にデータセットの属性からフィーチャを生成します。 一般に、これは、機械設計のアプローチにとって最も重要なプロセスです。これは、フィーチャデザインがラベリングの精度に大きく影響するためです。 このチュートリアルでは、位置の単語(シーケンスの先頭からのオフセット)の単語から19種類の属性を抽出します。

  • w[t-2], w[t-1], w[t], w[t+1], w[t+2],
  • w[t-1]|w[t], w[t]|w[t+1],
  • pos[t-2], pos[t-1], pos[t], pos[t+1], pos[t+2],
  • pos[t-2]|pos[t-1], pos[t-1]|pos[t], pos[t]|pos[t+1], pos[t+1]|pos[t+2],
  • pos[t-2]|pos[t-1]|pos[t], pos[t-1]|pos[t]|pos[t+1], pos[t]|pos[t+1]|pos[t+2]

このリストでは、w [t]とpos [t]は、それぞれ位置tの単語と品詞をシーケンスで表します。 これらの特徴は、w [t-1]およびpos [t + 1]などの周囲の単語からの情報を使用することによって、位置tでの単語の特性を表す。 たとえば、次の例のトークン 'the'は、

        He PRP B-NP
        reckons VBZ B-VP
  t --> the DT B-NP
        current JJ I-NP
        account NN I-NP

これらの属性を取得する(簡単のため、位置tは省略)。

  • w[-2]=He, w[-1]=reckons, w[0]=the, w[1]=current, w[2]=account
  • w[-1]|w[0]=reckons|the, w[0]|w[1]=the|current
  • pos[-2]=PRP, pos[-1]=VBZ, pos[0]=DT, pos[1]=JJ, pos[2]=NN
  • pos[-2]|pos[-1]=PRP|VBZ, pos[-1]|pos[0]=VBZ|DT, pos[0]|pos[1]=DT|JJ, pos[1]|pos[2]=JJ|NN
  • pos[-2]|pos[-1]|pos[0]=PRP|VBZ|DT, pos[-1]|pos[0]|pos[1]=VBZ|DT|JJ, pos[0]|pos[1]|pos[2]=DT|JJ|NN

この例では、属性「w [0] = the」は、現在のトークンが「the」であるイベントを提示し、属性「pos [0] | pos [1] | pos [2] = DT | JJ | NN現在、次、および2単語先の品詞がそれぞれDT、JJ、NNであるイベントを提示する。 CRFsuiteは、これらの属性(例えば、「pos [0] | pos [1] | pos [2] = DT | JJ | NN」)とラベル(例えば、「B-NP」)との間の関連を学習し、指定されたテキスト属性は "name = value"という規約に従う必要はありません(例: "w [0] = the")。 CRFsuiteは、文字列にコロン文字(属性名とその重みを区切るために使用)が含まれていない限り、任意の文字列を属性名として受け入れます。 "name = value"という規約は単に属性名を解釈するためのものです。

CRFsuiteには、項目行がラベルで始まり、その属性がTAB( '\ t')文字で区切られたデータセットが必要です(詳細は文書を参照)。訓練/試験データからCRFsuiteデータへの変換を実装することは困難ではない。変換の実装として、CRFsuiteディストリビューションには、CoNLL 2000データから属性を生成するPythonスクリプトchunking.pyが含まれています。以下の手順では、train.txt.gzとtest.txt.gzをCRFsuiteデータ形式と互換性のあるtrain.crfsuite.txtとtest.crfsuite.txtに変換します。

$ zcat train.txt.gz | ./chunking.py > train.crfsuite.txt
$ zcat test.txt.gz | ./chunking.py > test.crfsuite.txt
$ less train.crfsuite.txt
... (snip) ...

B-NP    w[0]=He w[1]=reckons    w[2]=the        w[0]|w[1]=He|reckons    pos[0]=P
RP      pos[1]=VBZ      pos[2]=DT       pos[0]|pos[1]=PRP|VBZ   pos[1]|pos[2]=VB
Z|DT    pos[0]|pos[1]|pos[2]=PRP|VBZ|DT __BOS__
B-VP    w[-1]=He        w[0]=reckons    w[1]=the        w[2]=current    w[-1]|w[
0]=He|reckons   w[0]|w[1]=reckons|the   pos[-1]=PRP     pos[0]=VBZ      pos[1]=D
T       pos[2]=JJ       pos[-1]|pos[0]=PRP|VBZ  pos[0]|pos[1]=VBZ|DT    pos[1]|p
os[2]=DT|JJ     pos[-1]|pos[0]|pos[1]=PRP|VBZ|DT        pos[0]|pos[1]|pos[2]=VBZ
|DT|JJ
B-NP    w[-2]=He        w[-1]=reckons   w[0]=the        w[1]=current    w[2]=acc
ount    w[-1]|w[0]=reckons|the  w[0]|w[1]=the|current   pos[-2]=PRP     pos[-1]=
VBZ     pos[0]=DT       pos[1]=JJ       pos[2]=NN       pos[-2]|pos[-1]=PRP|VBZ 
pos[-1]|pos[0]=VBZ|DT   pos[0]|pos[1]=DT|JJ     pos[1]|pos[2]=JJ|NN     pos[-2]|
pos[-1]|pos[0]=PRP|VBZ|DT       pos[-1]|pos[0]|pos[1]=VBZ|DT|JJ pos[0]|pos[1]|po
s[2]=DT|JJ|NN
I-NP    w[-2]=reckons   w[-1]=the       w[0]=current    w[1]=account    w[2]=def
icit    w[-1]|w[0]=the|current  w[0]|w[1]=current|account       pos[-2]=VBZ
     pos[-1]=DT      pos[0]=JJ       pos[1]=NN       pos[2]=NN       pos[-2]|pos
[-1]=VBZ|DT  pos[-1]|pos[0]=DT|JJ    pos[0]|pos[1]=JJ|NN     pos[1]|pos[2]=NN|NN
     pos[-2]|pos[-1]|pos[0]=VBZ|DT|JJ        pos[-1]|pos[0]|pos[1]=DT|JJ|NN  pos
[0]|pos[1]|pos[2]=JJ|NN|NN
I-NP    w[-2]=the       w[-1]=current   w[0]=account    w[1]=deficit    w[2]=wil
l       w[-1]|w[0]=current|account      w[0]|w[1]=account|deficit       pos[-2]=
DT      pos[-1]=JJ      pos[0]=NN       pos[1]=NN       pos[2]=MD       pos[-2]|
pos[-1]=DT|JJ   pos[-1]|pos[0]=JJ|NN    pos[0]|pos[1]=NN|NN     pos[1]|pos[2]=NN
|MD     pos[-2]|pos[-1]|pos[0]=DT|JJ|NN pos[-1]|pos[0]|pos[1]=JJ|NN|NN  pos[0]|p
os[1]|pos[2]=NN|NN|MD

... (snip) ...

トレーニング

これでCRFsuiteをトレーニングに使用する準備が整いました。 train.crfsuite.txtからCRFモデルを訓練するには、次のコマンドを入力します。 CRFsuiteは、訓練データを読み取り、データに基づいて必要な状態(属性ラベル)および遷移(bigramラベル)を生成し、条件付き確率分布の対数尤度を最大にし、モデルをCoNLL2000.modelに格納する。

$ crfsuite learn -m CoNLL2000.model train.crfsuite.txt
CRFSuite 0.12  Copyright (c) 2007-2011 Naoaki Okazaki

Start time of the training: 2011-06-25T14:52:13Z

Reading the data set(s)
[1] train.crfsuite.txt
0....1....2....3....4....5....6....7....8....9....10
Number of instances: 8937
Seconds required: 5.890

Statistics the data set(s)
Number of data sets (groups): 1
Number of instances: 8936
Number of items: 211727
Number of attributes: 335674
Number of labels: 22

Feature generation
type: CRF1d
feature.minfreq: 0.000000
feature.possible_states: 0
feature.possible_transitions: 0
0....1....2....3....4....5....6....7....8....9....10
Number of features: 452755
Seconds required: 2.140

L-BFGS optimization
c1: 0.000000
c2: 1.000000
num_memories: 6
max_iterations: 2147483647
epsilon: 0.000010
stop: 10
delta: 0.000010
linesearch: MoreThuente
linesearch.max_iterations: 20

***** Iteration #1 *****
Log-likelihood: -275528.648286
Feature norm: 5.000000
Error norm: 44363.015822
Active features: 452755
Line search trials: 2
Line search step: 0.000050
Seconds required for this iteration: 4.860

***** Iteration #2 *****
Log-likelihood: -164450.778877
Feature norm: 9.067189
Error norm: 26619.939310
Active features: 452755
Line search trials: 1
Line search step: 1.000000
Seconds required for this iteration: 1.630

... (snip) ...

***** Iteration #165 *****
Log-likelihood: -13139.375165
Feature norm: 81.074163
Error norm: 2.638386
Active features: 452755
Line search trials: 1
Line search step: 1.000000
Seconds required for this iteration: 1.660

L-BFGS terminated with the stopping criteria
Total seconds required for training: 293.610

Storing the model
Number of active features: 452755 (452755)
Number of active attributes: 335674 (335674)
Number of active labels: 22 (22)
Writing labels
Writing attributes
Writing feature references for transitions
Writing feature references for attributes
Seconds required: 0.730

End time of the training: 2011-06-25T14:57:15Z

CRFモデルをトレーニングし、テストデータで評価されたパフォーマンス(精度、精度、リコール、f1スコア)を確認することもできます。 訓練プロセスが進むにつれて、あなたのモデルが改善されていることを知ることはエキサイティングなことです。 次のコマンドラインは、オプション(-e2)を使用してデータセット#2(test.crfsuite.txt)のホールドアウト評価を実行します。

$ crfsuite learn -e2 train.crfsuite.txt test.crfsuite.txt
CRFSuite 0.12  Copyright (c) 2007-2011 Naoaki Okazaki

Start time of the training: 2011-06-25T16:07:40Z

Reading the data set(s)
[1] train.crfsuite.txt
0....1....2....3....4....5....6....7....8....9....10
Number of instances: 8937
Seconds required: 5.870
[2] test.crfsuite.txt
0....1....2....3....4....5....6....7....8....9....10
Number of instances: 2013
Seconds required: 1.370

Statistics the data set(s)
Number of data sets (groups): 2
Number of instances: 10948
Number of items: 259104
Number of attributes: 387579
Number of labels: 23

Holdout group: 2

Feature generation
type: CRF1d
feature.minfreq: 0.000000
feature.possible_states: 0
feature.possible_transitions: 0
0....1....2....3....4....5....6....7....8....9....10
Number of features: 452755
Seconds required: 2.150

L-BFGS optimization
c1: 0.000000
c2: 1.000000
num_memories: 6
max_iterations: 2147483647
epsilon: 0.000010
stop: 10
delta: 0.000010
linesearch: MoreThuente
linesearch.max_iterations: 20

***** Iteration #1 *****
Log-likelihood: -279935.059188
Feature norm: 5.000000
Error norm: 45136.783202
Active features: 452755
Line search trials: 2
Line search step: 0.000050
Seconds required for this iteration: 5.230
Performance by label (#match, #model, #ref) (precision, recall, F1):
    B-NP: (8312, 10265, 12422) (0.8097, 0.6691, 0.7328)
    B-PP: (3986, 6030, 4811) (0.6610, 0.8285, 0.7354)
    I-NP: (14116, 27744, 14376) (0.5088, 0.9819, 0.6703)
    B-VP: (0, 0, 4658) (0.0000, 0.0000, 0.0000)
    I-VP: (0, 0, 2646) (0.0000, 0.0000, 0.0000)
    B-SBAR: (0, 0, 535) (0.0000, 0.0000, 0.0000)
    O: (3298, 3338, 6180) (0.9880, 0.5337, 0.6930)
    B-ADJP: (0, 0, 438) (0.0000, 0.0000, 0.0000)
    B-ADVP: (0, 0, 866) (0.0000, 0.0000, 0.0000)
    I-ADVP: (0, 0, 89) (0.0000, 0.0000, 0.0000)
    I-ADJP: (0, 0, 167) (0.0000, 0.0000, 0.0000)
    I-SBAR: (0, 0, 4) (0.0000, 0.0000, 0.0000)
    I-PP: (0, 0, 48) (0.0000, 0.0000, 0.0000)
    B-PRT: (0, 0, 106) (0.0000, 0.0000, 0.0000)
    B-LST: (0, 0, 5) (0.0000, 0.0000, 0.0000)
    B-INTJ: (0, 0, 2) (0.0000, 0.0000, 0.0000)
    I-INTJ: (0, 0, 0) (******, ******, ******)
    B-CONJP: (0, 0, 9) (0.0000, 0.0000, 0.0000)
    I-CONJP: (0, 0, 13) (0.0000, 0.0000, 0.0000)
    I-PRT: (0, 0, 0) (******, ******, ******)
    B-UCP: (0, 0, 0) (******, ******, ******)
    I-UCP: (0, 0, 0) (******, ******, ******)
    I-LST: (0, 0, 2) (0.0000, 0.0000, 0.0000)
Macro-average precision, recall, F1: (0.129025, 0.131010, 0.123104)
Item accuracy: 29712 / 47377 (0.6271)
Instance accuracy: 23 / 2012 (0.0114)

... (snip) ...

***** Iteration #162 *****
Log-likelihood: -13143.933308
Feature norm: 81.103204
Error norm: 2.207139
Active features: 452755
Line search trials: 1
Line search step: 1.000000
Seconds required for this iteration: 1.980
Performance by label (#match, #model, #ref) (precision, recall, F1):
    B-NP: (12013, 12374, 12422) (0.9708, 0.9671, 0.9689)
    B-PP: (4713, 4878, 4811) (0.9662, 0.9796, 0.9729)
    I-NP: (13998, 14497, 14376) (0.9656, 0.9737, 0.9696)
    B-VP: (4470, 4668, 4658) (0.9576, 0.9596, 0.9586)
    I-VP: (2551, 2700, 2646) (0.9448, 0.9641, 0.9544)
    B-SBAR: (449, 499, 535) (0.8998, 0.8393, 0.8685)
    O: (5945, 6122, 6180) (0.9711, 0.9620, 0.9665)
    B-ADJP: (322, 403, 438) (0.7990, 0.7352, 0.7658)
    B-ADVP: (711, 836, 866) (0.8505, 0.8210, 0.8355)
    I-ADVP: (54, 82, 89) (0.6585, 0.6067, 0.6316)
    I-ADJP: (110, 137, 167) (0.8029, 0.6587, 0.7237)
    I-SBAR: (2, 15, 4) (0.1333, 0.5000, 0.2105)
    I-PP: (34, 42, 48) (0.8095, 0.7083, 0.7556)
    B-PRT: (80, 102, 106) (0.7843, 0.7547, 0.7692)
    B-LST: (0, 0, 5) (0.0000, 0.0000, 0.0000)
    B-INTJ: (1, 1, 2) (1.0000, 0.5000, 0.6667)
    I-INTJ: (0, 0, 0) (******, ******, ******)
    B-CONJP: (5, 8, 9) (0.6250, 0.5556, 0.5882)
    I-CONJP: (10, 13, 13) (0.7692, 0.7692, 0.7692)
    I-PRT: (0, 0, 0) (******, ******, ******)
    B-UCP: (0, 0, 0) (******, ******, ******)
    I-UCP: (0, 0, 0) (******, ******, ******)
    I-LST: (0, 0, 2) (0.0000, 0.0000, 0.0000)
Macro-average precision, recall, F1: (0.604705, 0.576296, 0.581536)
Item accuracy: 45468 / 47377 (0.9597)
Instance accuracy: 1176 / 2012 (0.5845)

L-BFGS terminated with the stopping criteria
Total seconds required for training: 339.800

End time of the training: 2011-06-25T16:13:29Z

このログメッセージは、トレーニングデータから得られたCRFモデルが95.97%のアイテム精度を達成したことを報告しています。

タグ付け

テストデータにCRFモデルとチャンクラベルを適用することができます。 CoNLL 2000共有タスクによって配布されたテストデータにはチャンクラベルが付いています(評価目的のため)、CRFsuiteは既存のラベルを無視し、モデルによって予測されたラベルシーケンス(1行につき1ラベル、空白で区切られたラベル)を出力します。

$ cat test.crfsuite.txt
B-NP    w[0]=Rockwell   w[1]=International      w[2]=Corp.      w[0]|w[1]=Rockwe
ll|International        pos[0]=NNP      pos[1]=NNP      pos[2]=NNP      pos[0]|p
os[1]=NNP|NNP   pos[1]|pos[2]=NNP|NNP   pos[0]|pos[1]|pos[2]=NNP|NNP|NNP
        __BOS__
I-NP    w[-1]=Rockwell  w[0]=International      w[1]=Corp.      w[2]='s w[-1]|w[
0]=Rockwell|International       w[0]|w[1]=International|Corp.   pos[-1]=NNP
     pos[0]=NNP      pos[1]=NNP      pos[2]=POS      pos[-1]|pos[0]=NNP|NNP  pos
[0]|pos[1]=NNP|NNP   pos[1]|pos[2]=NNP|POS   pos[-1]|pos[0]|pos[1]=NNP|NNP|NNP  
     pos[0]|pos[1]|pos[2]=NNP|NNP|POS
... (snip) ...

$ crfsuite tag -m CoNLL2000.model test.crfsuite.txt
B-NP
I-NP
I-NP
B-NP
I-NP
I-NP
B-VP
B-NP
B-VP
B-NP
I-NP
I-NP
B-VP
B-NP
I-NP
B-PP
B-NP
I-NP
B-VP
I-VP
B-NP
I-NP
B-PP
B-NP
B-NP
I-NP
I-NP
O

... (snip) ...

CRFsuiteは、(test.crfsuite.txt内の)参照ラベルとTAB文字で区切られた予測ラベルの両方を出力できます。 この例では、各行の左のラベルは入力データ(test.crfsuite.txt)に書き込まれた参照ラベルを表し、右のラベルは予測されたラベルを表します。 この機能は、タグ付け結果の評価に役立ちます。

$ crfsuite tag -r -m CoNLL2000.model test.crfsuite.txt
B-NP    B-NP
I-NP    I-NP
I-NP    I-NP
B-NP    B-NP
I-NP    I-NP
I-NP    I-NP
B-VP    B-VP
B-NP    B-NP
B-VP    B-VP
B-NP    B-NP
I-NP    I-NP
I-NP    I-NP
B-VP    B-VP
B-NP    B-NP
I-NP    I-NP
B-PP    B-PP
B-NP    B-NP
I-NP    I-NP
B-VP    B-VP
I-VP    I-VP
B-NP    B-NP
I-NP    I-NP
B-PP    B-PP
B-NP    B-NP
B-NP    B-NP
I-NP    I-NP
I-NP    I-NP
O       O

... (snip) ...

CRFsuiteは、 "-qt"オプション付きのラベル付きテストデータを使用してCRFモデルを評価することもできます。

$ crfsuite tag -qt -m CoNLL2000.model test.crfsuite.txt
Performance by label (#match, #model, #ref) (precision, recall, F1):
    B-NP: (12000, 12358, 12407) (0.9710, 0.9672, 0.9691)
    B-PP: (4707, 4872, 4805) (0.9661, 0.9796, 0.9728)
    I-NP: (13984, 14484, 14359) (0.9655, 0.9739, 0.9697)
    B-VP: (4466, 4662, 4653) (0.9580, 0.9598, 0.9589)
    I-VP: (2549, 2698, 2643) (0.9448, 0.9644, 0.9545)
    B-SBAR: (448, 498, 534) (0.8996, 0.8390, 0.8682)
    O: (5939, 6113, 6174) (0.9715, 0.9619, 0.9667)
    B-ADJP: (322, 403, 438) (0.7990, 0.7352, 0.7658)
    B-ADVP: (711, 835, 866) (0.8515, 0.8210, 0.8360)
    I-ADVP: (54, 82, 89) (0.6585, 0.6067, 0.6316)
    I-ADJP: (110, 137, 167) (0.8029, 0.6587, 0.7237)
    I-SBAR: (2, 15, 4) (0.1333, 0.5000, 0.2105)
    I-PP: (34, 42, 48) (0.8095, 0.7083, 0.7556)
    B-PRT: (80, 102, 106) (0.7843, 0.7547, 0.7692)
    B-LST: (0, 0, 4) (0.0000, 0.0000, 0.0000)
    B-INTJ: (1, 1, 2) (1.0000, 0.5000, 0.6667)
    I-INTJ: (0, 0, 0) (******, ******, ******)
    B-CONJP: (5, 7, 9) (0.7143, 0.5556, 0.6250)
    I-CONJP: (10, 12, 13) (0.8333, 0.7692, 0.8000)
    I-PRT: (0, 0, 0) (******, ******, ******)
    B-UCP: (0, 0, 0) (******, ******, ******)
    I-UCP: (0, 0, 0) (******, ******, ******)
Macro-average precision, recall, F1: (0.639239, 0.602512, 0.611086)
Item accuracy: 45422 / 47321 (0.9599)
Instance accuracy: 1176 / 2011 (0.5848)
Elapsed time: 0.940000 [sec] (2140.4 [instance/sec])

モデルファイルのダンプ

CRFモデルの精度を改善するときは、トレーナーが指定した特徴量を確認すると便利です。 効率性の理由から、CRFsuiteはモデルをバイナリ形式で保存するため、モデルファイルを読み込むことはできません。 したがって、dumpコマンドを使用して、プレーンテキスト形式のモデルを読み取る必要があります。

$ crfsuite dump CoNLL2000.model
FILEHEADER = {
  magic: lCRF
  size: 28242501
  type: FOMC
  version: 100
  num_features: 0
  num_labels: 23
  num_attrs: 338547
  off_features: 0x30
  off_labels: 0x8B4EE4
  off_attrs: 0x8B5A0C
  off_labelrefs: 0x169C145
  off_attrrefs: 0x169C515
}

LABELS = {
      0: B-NP
      1: B-PP
      2: I-NP
      3: B-VP
      4: I-VP
      5: B-SBAR
      6: O
      7: B-ADJP
      8: B-ADVP
      9: I-ADVP
     10: I-ADJP
     11: I-SBAR
     12: I-PP
     13: B-PRT
     14: B-LST
     15: B-INTJ
     16: I-INTJ
     17: B-CONJP
     18: I-CONJP
     19: I-PRT
     20: B-UCP
     21: I-UCP
     22: I-LST
}

ATTRIBUTES = {
      0: U00=
      1: U01=
      2: U02=Confidence
      3: U03=in
      4: U04=the
      5: U05=/Confidence
      6: U06=Confidence/in
      7: U10=
... (snip) ...
}

TRANSITIONS = {
  (1) B-NP --> B-NP: 2.327985
  (1) B-NP --> B-PP: 4.391125
  (1) B-NP --> I-NP: 30.372649
  (1) B-NP --> B-VP: 7.725525
  (1) B-NP --> B-SBAR: 1.821388
  (1) B-NP --> O: 3.805715
  (1) B-NP --> B-ADJP: 4.801651
  (1) B-NP --> B-ADVP: 3.842473
... (snip) ...
}

TRANSITIONS_FROM_BOS = {
  (2) BOS --> B-NP: 17.875605
  (2) BOS --> B-PP: -0.318745
  (2) BOS --> I-NP: -4.387101
  (2) BOS --> B-VP: -0.383031
  (2) BOS --> I-VP: -1.163315
  (2) BOS --> B-SBAR: 1.368176
  (2) BOS --> O: 2.783132
... (snip) ...
}

TRANSITIONS_TO_EOS = {
  (3) B-NP --> EOS: 16.156051
  (3) B-PP --> EOS: -1.045312
  (3) I-NP --> EOS: -2.762051
  (3) B-VP --> EOS: -0.767247
  (3) I-VP --> EOS: -1.113502
  (3) B-SBAR --> EOS: -2.407145
  (3) O --> EOS: 4.131429
... (snip) ...
}

STATE_FEATURES = {
  (0) U00= --> B-NP: -2.622045
  (0) U00= --> B-PP: -1.562976
  (0) U00= --> I-NP: -2.555526
  (0) U00= --> B-VP: -1.329829
  (0) U00= --> I-VP: -1.152970
  (0) U00= --> B-SBAR: -2.590170
  (0) U00= --> O: -1.584688
  (0) U00= --> B-ADJP: -1.526879
... (snip) ...
}

属性エクストラクタの記述に関する注意

このチュートリアルでは、CRFsuiteディストリビューションにバンドルされている chunking.py を使用して、データセットから属性を抽出しました。 実際には、目標タスクに適した属性抽出器を実装する必要があります。 任意のプログラミング言語で任意の方法で属性抽出プログラムを書くことができます。 ただし、データに固定長のフィールド(CoNLL 2000データセットなど)があり、Pythonに精通している場合は、chunking.pyのコードを変更することをお勧めします。 このセクションでは、chunking.pyスクリプトを変更する人のためのスクリプトの構造について説明します。

以下はchunking.pyの実装です:

#!/usr/bin/env python

"""
An attribute extractor for chunking.
Copyright 2010,2011 Naoaki Okazaki.
"""

# Separator of field values.
separator = ' '

# Field names of the input data.
fields = 'w pos y'

# Attribute templates.
templates = (
    (('w', -2), ),
    (('w', -1), ),
    (('w',  0), ),
    (('w',  1), ),
    (('w',  2), ),
    (('w', -1), ('w',  0)),
    (('w',  0), ('w',  1)),
    (('pos', -2), ),
    (('pos', -1), ),
    (('pos',  0), ),
    (('pos',  1), ),
    (('pos',  2), ),
    (('pos', -2), ('pos', -1)),
    (('pos', -1), ('pos',  0)),
    (('pos',  0), ('pos',  1)),
    (('pos',  1), ('pos',  2)),
    (('pos', -2), ('pos', -1), ('pos',  0)),
    (('pos', -1), ('pos',  0), ('pos',  1)),
    (('pos',  0), ('pos',  1), ('pos',  2)),
    )


import crfutils

def feature_extractor(X):
    # Apply feature templates to obtain features (in fact, attributes)
    crfutils.apply_templates(X, templates)
    if X:
        # Append BOS and EOS features manually
        X[0]['F'].append('__BOS__')     # BOS feature
        X[-1]['F'].append('__EOS__')    # EOS feature

if __name__ == '__main__':
    crfutils.main(feature_extractor, fields=fields, sep=separator)

共通のスタッフ(テンプレート、データI / Oなどからの属性生成)が他のモジュール crfutils.pytemplate.py で実装されているため、実装は非常に簡単です。 chunking.pyスクリプトは3つの重要な変数を定義しています:

  • セパレータ
    • 入力データの区切り文字。これはコマンドライン引数( "-s"オプション)で上書きすることができます。この例では、フィールドの区切り文字としてスペース文字を想定しています。
  • フィールド
    • 空白文字で区切られた入力データのフィールド名(左から右の順)。これはコマンドライン引数( "-f"オプション)で上書きすることができます。この例では、入力データの各行が "w"、 "pos"、および "y"という名前のフィールドで構成されていると仮定しています。
  • テンプレート
    • Pythonタプル/リストオブジェクトとして書かれた属性(フィーチャ)テンプレート

入力データに対してこれらの変数を変更するだけで十分です。テンプレート内の各要素は、(name、offset)ペアのタプル/リストであり、名前はフィールド名を表し、offsetは現在の位置へのオフセットを表します。たとえば、タプル、

  (('w', -2), ),

現在の位置の前に2つのトークンで 'w'フィールドの値を抽出します。 1つの要素( 'w'、-2)を持つタプルを定義するには、( 'w'、-2)の後のコンマが必要であることに注意してください。 タプル、

  (('w', -1), ('w',  0)),

前のトークンでの「w」フィールドの値と、現在の位置(すなわち、前のトークンで始まるバイグラム)における「w」フィールドの値とを連結する属性を定義する。

関数feature_extractorは、入力データから読み込まれた一連の項目(この例ではX)を受け取り、必要な属性を生成します。引数Xはアイテムのリストを表します。各項目は、フィールド名からその値へのマッピング(辞書)オブジェクトによって表されます。 CoNLLチャンク処理では、X [0] [ 'w']はシーケンス内の最初のアイテムの単語を表し、X [0] [ 'pos']はシーケンス内の最後のアイテムの品詞タグを表します。

X内の各項目のマッピングオブジェクトには、アイテムのために生成された属性を格納する値(リストオブジェクト)を持つ特別なキー 'F'があります。属性リストの各要素は、文字列または(name、value)のタプル(重み付きの属性)のいずれかでなければなりません。 chunking.pyスクリプトでは、crfutils.apply_templates(属性リストを満たす可能性があります)を使ってフィーチャテンプレートが適用されます。この例では、シーケンスの最初と最後に特別な属性 "BOS"と "EOS"も生成します。

他のタスク用のフィーチャ抽出

chunking.pyに加えて、サンプルディレクトリには次のものが含まれています。

  • 品詞タグ付けのための pos.py
    • コードの構造は chunking.py の構造に似ています。フィールド記述子と属性テンプレートのみが異なります。
  • 名前付きエンティティ認識のための ner.py
    • このスクリプトは、入力データから様々な特性(例えば、トークンの文字形状、接頭辞および接尾辞)を抽出するため、より複雑である。
  • CRF ++と互換性のあるテンプレートを使用するための template.py
    • 属性とバイグラムのラベル付きの機能はサポートされていません。
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment