Kouhei Sutou
kou****@clear*****
2015年 4月 23日 (木) 12:18:44 JST
須藤です。
森さん、grn_patでの有効なノードの確認方法について教えてくだ
さい。
知りたいことは次の2つです。
* 有効な子ノードが親ノードのcheckと同じケースはありえるの
か(実際にあるんで、それが意図したものなのかを知りたい)
* 有効な子ノードのcheckが0のケースはありえるのか
(こっちも実際にあるんで、それが意図したものなのかを知り
たい)
詳細は次の通りです。
森さんに直してもらった_grn_pat_del()の問題の再現に使ったデー
タでは、grn_p(ctx, pat)(patの中身を読みやすい形で表示する関
数)が期待通りに動かないことがわかりました。具体的には
1. grn_pat_add("2")
2. grn_pat_add("1")
3. grn_pat_add("3")
とした状態で"3"のノードの中身を表示しません。実際の表示は次
のようになっています。
#<table:pat names key:ShortText value:(nil) size:3 columns:[] default_tokenizer:(nil) normalizer:(nil) keys:["1", "2", "3"] subrec:none nodes:{
2("1"){0,6,0}[00110001]
L:2
R:1("2"){0,7,0}[00110010]
L:1
R:3
}>
解説すると、
--
2("1"){0,6,0}[00110001]
L:2
R:1("2"){0,7,0}[00110010]
L:1
R:3
--
のところがpatの中身です。
「L:」が付いているのはpat_node::lrの[0]の方で
「R:」が付いているのはpat_node::lrの[1]の方です。
一番上の「L:」も「R:」も付いていないやつは最初のノードです。
「L:」、「R:」の右側にある数字はPAT_AT()したときに使った
grn_idです。
キーがあると判断したところでは
(#{キー}){#{checkの中身}}[#{キーのバイト列}]
というフォーマットでpat_nodeの中身を表示しています。
なお、
{#{checkの中身}}
は
{#{nth_byte},#{nth_bit},#{terminated}}
というように16ビットに詰め込んだ情報を分割して表示しています。
で、これを
--
2("1"){0,6,0}[00110001]
L:2
R:1("2"){0,7,0}[00110010]
L:1
R:3 ←が「R:3("3"){...}[...]」となってほしい!!
--
というようにしたいです。
grn_p(ctx, pat)の実装(grn_pat_inspect_node())では、
https://github.com/groonga/groonga/blob/master/lib/pat.c#L50-L51
の
typedef struct {
grn_id lr[2];
/*
...
The both available nodes has larger check value rather
than the current node.
...
*/
...;
} pat_node;
というコメントを信じてcheckの値を使って
https://github.com/groonga/groonga/blob/master/lib/pat.c#L2370
if (c > check) {
というように、そのノードのキーを表示するかどうかを判断してい
ます。
が、この条件だと「"3"」のノードを有効なノードと判断できませ
ん。
というのは、このケースでは↓というように「"2"」のノードと
「"3"」のノードのcheckが同じ値(14)になっているからです。
--
2("1"){0,6,0}[00110001]
L:2
R:1("2"){0,7,0}[00110010]
L:1
R:3("3"){0,7,0}[00110011]
--
これは妥当なケース(意図した動作)なんでしょうか?(質問1)
妥当なケースならgrn_pat_inspect_node()でもこのケースに対応し
ようと思っています。
で、もうひとつのケースは
1. grn_pat_add("2")
2. grn_pat_add("1")
3. grn_pat_add("3")
の後に
4. grn_pat_del("2")
をした状態のケースです。
この状態ではpatの中身は次のようになっています。
--
2("1"){0,6,0}[00110001]
L:2
R:3("3"){0,0,0}[00110011]
--
気になるところは「"3"」のノードのcheckが0なことです。
これは妥当なケース(意図した動作)なんでしょうか?(質問2)
妥当なケースならgrn_pat_inspect_node()でもこのケースに対応し
ようと思っています。
ちなみに、
1. grn_pat_add("1")
2. grn_pat_add("3")
とすると次のようになり、checkは14になります。
--
2("1"){0,6,0}[00110001]
L:2
R:1("3"){0,7,0}[00110011]
L:0
R:1("3"){0,7,0}[00110011]
--
--
須藤 功平 <kou****@clear*****>
株式会社クリアコード <http://www.clear-code.com/>
Groongaベースの全文検索システムを総合サポート:
http://groonga.org/ja/support/
パッチ採用 - プログラミングが楽しい人向けの採用プロセス:
http://www.clear-code.com/recruitment/
コードリーダー育成支援 - 自然とリーダブルコードを書くチームへ:
http://www.clear-code.com/services/code-reader/