Senna_Records クラス

class Senna_Records implements Traversable, Countable

Senna_Recordsクラスは、検索結果を表現するクラスです。

検索結果は0個以上のレコード(Senna_Records_Row)の集合で、レコードは0個以上のサブレコード(Senna_Records_SubRecords)を格納します。


クラス概要

Senna_Recordsのインスタンスを生成する方法は2通りあります。1つ目はSenna_Indexクラスのquery()で検索結果を得る方法です。こちらの方がシンプルです。

<?php
// (検索結果を得る)
$i = Senna_Index::open('/path/to/index');
$records = $i->query('楽しい 全文検索');

echo $records->count();    // 検索結果の件数を取得する
$records->setLimit(300);   // 検索結果の上限を300件に設定する
echo $records->getLimit(); // 検索結果の上限を取得する

$page1 = $records->slice(0, 10);  // 上位10件を取得する
$page2 = $records->slice(10, 10); // 11位から20位までを取得する
$page3 = $records->slice(20, 10); // 21位から30位までを取得する

// 全ての検索結果を表示する。Traversableを実装しているのでforeachで反復処理できる
foreach ($records as $row) {
   // 各レコード($row)はSenna_Records_Rowオブジェクト
   echo $row->getKey(), ' = ', $row->getScore(), "\n";
}

$records->match('PHP エクステンション'); // 絞り込み検索
$records->add('senna');                  // 検索結果に追加
$records->remove('NGワード あぼーん');   // 検索結果から除外

// 文書ID「doc001」のスコアが何点か調べる
echo $records->scoreOf('doc001');

// 長すぎて無視したクエリー文字列を取得する
$records = $index->query('+指定した +数以上の -演算子は OR 無視 +する', 3);
echo $records->getIgnoredQueryString();

もう1つは、コンストラクタを呼んで生成する方法です。こちらの方法を使うと、レコード単位を変更したり、各レコードにサブレコード情報を持たせることが可能になります。まず空のSenna_Recordsオブジェクトを生成し、add()でクエリーを発行して検索結果を追加する、という流れになります。

<?php
$i = Senna_Index::open('/path/to/index');

// サブレコード情報を格納できる検索結果を作る。この例のサブレコードは「段落」単位
$records = new Senna_Records($i, Senna_Records::DOCUMENT, Senna_Records::SECTION, 20);
$records->add('Senna 快適全文検索');

$list = $records->slice(0, 10);
foreach ($list as $row) {
  echo $row->getKey(), "\n";
  foreach ($row->getSubRecords() as $subRow) {
    // 各文書のどの段落でヒットしたかわかるようになる
    printf("\tsection: %d, score: %d\n", $subRow->getSection(), $subRow->getScore());
  }
}

// 検索単位を段落単位に設定する
$records = new Senna_Records($i, Senna_Records::SECTION);
$records->add('Senna 快適全文検索');

制限事項

Senna_RecordsTraversableインターフェイスを実装しているため、配列のようにforeachループで各レコードを反復処理することができます。ただし、反復処理中はそのオブジェクトに対して以下のメソッドを呼べません。呼んだ場合はフェイルファストのためにBadMethodCallExceptionを投げます。

scoreOf(), slice(), add(), adjust(), match(), remove()

これらのメソッドは、内部的なカーソルを移動またはリセットします。foreachループで反復処理する際にも同じ内部カーソルを移動するため、予測できない動作を回避する目的で、ただちに例外を投げる仕様になっています。

そのため、BadMethodCallExceptionを補足するtry-catchを書くことは誤りです。この例外が発生しましたらコードの修正が必要ですので、例えば次のようなループ外でメソッドを呼ぶコードに書き換えてください。

// ある文書(doc01)との相対スコアを計算する
$base = $records->scoreOf('doc01');
foreach ($records as $row) {
   //echo $row->getScore() - $records->scoreOf('doc01');  // NG
   echo $row->getScore() - $base;  // OK
}

クラス定数

レコード単位関連

  • DOCUMENT (integer)
    • 文書単位を表します。
  • SECTION (integer)
    • 段落単位を表します。
  • POSITION (integer)
    • 出現位置単位を表します。「出現位置」とは「何トークン目か」です。
  • NONE (integer)
    • サブレコードを格納しないことを表します。

クエリー関連

  • DEFAULT_MAX_N_SUBRECS (integer)
    • 検索結果の各レコードに格納する最大サブレコード数のデフォルト値です。
  • DEFAULT_MAX_N_EXPRS (integer)
    • クエリー発行時の最大演算子数のデフォルト値(32)です。

コンストラクタ

public void __construct(
    Senna_Index $index [, int $record_unit [, int $sub_records_unit [, int $max_n_subrecs ]]])

指定されたインデックスの空の検索結果を作成します。このコンストラクタで空の検索を作成した後、add()でクエリーを発行して検索結果を追加してください。

検索結果の各レコードはrecord_unitで指定した単位になります。例えばレコード単位にSenna_Records::SECTIONを指定すると、段落単位での検索が可能になります。

サブレコードはsub_records_unitで指定した単位になります。各レコードは最大max_n_subrecs個のサブレコードを格納できます。サブレコード単位がSenna_Records::NONEの場合、サブレコードは格納しません。max_n_subrecsの値は常に0と解釈します。

  • パラメータ
    • index - 検索対象のインデックス
    • records_unit - 検索結果の単位。デフォルトはSenna_Records::DOCUMENTです。
    • sub_records_unit - 各レコードが格納するサブレコードの単位。デフォルトはSenna_Records::NONEです。
    • max_n_subrecs - 各レコードが格納する最大サブレコード数。デフォルトはSenna_Records::DEFAULT_MAX_N_SUBRECSです。
  • 例外
    • UnexpectedValueException - 以下の場合
      • records_unitSenna_Records::DOCUMENT, Senna_Records::SECTION, Senna_Records::POSITION以外
      • sub_records_unitSenna_Records::SECTION, Senna_Records::POSITION, Senna_Records::NONE以外
      • sub_records_unitrecords_unit以上の単位
      • max_n_subrecsが負の値
    • SennaException - 検索結果オブジェクトが生成できなかった場合
  • 関連項目

メソッド

getIgnoredQueryString

public string getIgnoredQueryString()

最後に実行したクエリーのうち、長すぎて無視した部分の文字列を返します。

  • 戻り値
    • 最後に実行したクエリーの無視した部分

scoreOf

public int scoreOf(string $key)

この検索結果内から指定された文書を探し、そのスコアを返します。該当する文書IDが検索結果にない場合は0を返します。

オブジェクト自身をforeachループで反復処理している間は、このメソッドを呼べません。呼んだ場合はBadMethodCallExceptionを投げます。

  • パラメータ
    • key - スコアを調べる文書ID
  • 戻り値
    • 指定した文書のスコア。該当文書が検索結果に含まれない場合は0
  • 例外
    • UnexpectedValueException - keyが空文字の場合
    • BadMethodCallException - オブジェクト自身をforeachで反復処理中にメソッドを呼んだ場合

slice

public array slice(int $offset, int $count)

この検索結果の一部を配列として切り出します。

検索結果の先頭(スコアの一番高いレコード)を0番目として、offset番目から最大count個を切り出します。配列の各要素はSenna_Records_Rowオブジェクトです。

offsetの値が検索結果の数以上の場合は、空の配列を返します。

オブジェクト自身をforeachループで反復処理している間は、このメソッドを呼べません。呼んだ場合はBadMethodCallExceptionを投げます。

  • パラメータ
    • offset - オフセット
    • count - 切り出す要素数
  • 戻り値
    • 切り出したレコードの配列
  • 例外
    • UnexpectedValueException - offsetが負の値、またはcountが1未満の場合
    • SennaException - レコード情報が取得できず、検索結果を切り出せなかった場合
    • BadMethodCallException - オブジェクト自身をforeachで反復処理中にメソッドを呼んだ場合

setLimit

public void setLimit(int $count)

この検索結果が保持できるレコード数の上限を設定します。

上限を無制限に設定する場合はcount0を指定してください。

  • パラメータ
    • count - レコード数の上限
  • 例外
    • UnexpectedValueException - countが負の値の場合

getLimit

public int getLimit()

この検索結果が保持できるレコード数の上限を返します。

上限が無制限の場合は0を返します。

  • 戻り値
    • オブジェクトが保持できるレコード数の上限。上限値に制限がない場合は0

count

public int count()

この検索結果が保持しているレコード数を返します。

setLimit()で設定した値を超えることはありません。

SPLが有効な場合、Senna_RecordsクラスはCountableインターフェイスを実装しますので、count()関数でも件数を取得できます。count($records);$records->count();のエイリアスになります。

  • 戻り値
    • 検索結果として保持しているレコード数

add

public Senna_Records add(string $query [, int $max_exprs])

この検索結果に、指定されたクエリーによる検索結果を追加します。

クエリーの書式はSennaのクエリー書式を参考にしてください。演算子を省略した場合は、+(AND演算子)が指定されたものして扱います。通常の検索エンジンでの検索クエリーと同じ使用感です。

最大max_exprs個までの演算子(キーワード)をクエリー文字列に含めることができます。max_exprs個を超えたものは無視します。無視した部分はgetIgnoredQueryString()で取得できます。

このメソッドはオブジェクト自身を返します。以下のようにメソッドを連続して呼ぶことができます。

<?php
$i = Senna_Index::open('/path/to/index');
$r = new Senna_Records($i);
$r->add('senna')
  ->add('検索エンジン')
  ->add('php エクステンション');
  • パラメータ
    • query - 検索クエリー文字列
    • max_exprs - クエリー内で使用する演算子の上限。デフォルトはSenna_Records::DEFAULT_MAX_N_EXPRSです。
  • 戻り値
    • オブジェクト自身
  • 例外
    • UnexpectedValueException - queryが空文字の場合、またはmax_exprsが1未満の場合
    • SennaException - 検索に失敗した場合
    • BadMethodCallException - オブジェクト自身をforeachで反復処理中にメソッドを呼んだ場合
  • 関連項目

adjust

public Senna_Records adjust(string $query [, int $max_exprs])

このメソッドは未実装です。実行してもスコア値は変化しません。

この検索結果に、指定されたクエリーによる検索結果が既に含まれていれば、そのレコードのスコア値を加算します。

クエリーの書式はSennaのクエリー書式を参考にしてください。演算子を省略した場合は、+(AND演算子)が指定されたものして扱います。通常の検索エンジンでの検索クエリーと同じ使用感です。

最大max_exprs個までの演算子(キーワード)をクエリー文字列に含めることができます。max_exprs個を超えたものは無視します。無視した部分はgetIgnoredQueryString()で取得できます。

このメソッドはオブジェクト自身を返します。以下のようにメソッドを連続して呼ぶことができます。

<?php
$i = Senna_Index::open('/path/to/index');
$r = new Senna_Records($i);
$r->add('senna')
  ->adjust('検索エンジン')
  ->adjust('php エクステンション');
  • パラメータ
    • query - 検索クエリー文字列
    • max_exprs - クエリー内で使用する演算子の上限。デフォルトはSenna_Records::DEFAULT_MAX_N_EXPRSです。
  • 戻り値
    • オブジェクト自身
  • 例外
    • UnexpectedValueException - queryが空文字の場合、またはmax_exprsが1未満の場合
    • SennaException - 検索に失敗した場合
    • BadMethodCallException - オブジェクト自身をforeachで反復処理中にメソッドを呼んだ場合
  • 関連項目

match

public Senna_Records match(string $query [, int $max_exprs])

この検索結果を、指定された条件で絞り込み検索します。

クエリーの書式はSennaのクエリー書式を参考にしてください。演算子を省略した場合は、+(AND演算子)が指定されたものして扱います。通常の検索エンジンでの検索クエリーと同じ使用感です。

最大max_exprs個までの演算子(キーワード)をクエリー文字列に含めることができます。max_exprs個を超えたものは無視します。無視した部分はgetIgnoredQueryString()で取得できます。

このメソッドはオブジェクト自身を返します。以下のようにメソッドを連続して呼ぶことができます。

<?php
$i = Senna_Index::open('/path/to/index');
$r = new Senna_Records($i);
$r->add('senna')
  ->match('検索エンジン')
  ->match('php エクステンション');
  • パラメータ
    • query - 検索クエリー文字列
    • max_exprs - クエリー内で使用する演算子の上限。デフォルトはSenna_Records::DEFAULT_MAX_N_EXPRSです。
  • 戻り値
    • オブジェクト自身
  • 例外
    • UnexpectedValueException - queryが空文字の場合、またはmax_exprsが1未満の場合
    • SennaException - 検索に失敗した場合
    • BadMethodCallException - オブジェクト自身をforeachで反復処理中にメソッドを呼んだ場合
  • 関連項目

remove

public Senna_Records remove(string $query [, int $max_exprs])

この検索結果から、指定された条件にマッチするレコードを除外します

クエリーの書式はSennaのクエリー書式を参考にしてください。演算子を省略した場合は、+(AND演算子)が指定されたものして扱います。通常の検索エンジンでの検索クエリーと同じ使用感です。

最大max_exprs個までの演算子(キーワード)をクエリー文字列に含めることができます。max_exprs個を超えたものは無視します。無視した部分はgetIgnoredQueryString()で取得できます。

このメソッドはオブジェクト自身を返します。以下のようにメソッドを連続して呼ぶことができます。

<?php
$i = Senna_Index::open('/path/to/index');
$r = new Senna_Records($i);
$r->add('senna')
  ->remove('検索エンジン')
  ->remove('php エクステンション');
  • パラメータ
    • query - 検索クエリー文字列
    • max_exprs - クエリー内で使用する演算子の上限。デフォルトはSenna_Records::DEFAULT_MAX_N_EXPRSです。
  • 戻り値
    • オブジェクト自身
  • 例外
    • UnexpectedValueException - queryが空文字の場合、またはmax_exprsが1未満の場合
    • SennaException - 検索に失敗した場合
    • BadMethodCallException - オブジェクト自身をforeachで反復処理中にメソッドを呼んだ場合
  • 関連項目

最終更新:2008/03/30 11:03