#
#  Copyright(C) 2007-2012 National Institute of Information and Communications Technology
#  


# Utility library
# SCRIPT: スクリプト名
# EXIT: ""以外の場合は異常終了(EXIT=終了ステータス)

# 形態素解析結果の取得
function ma(mrp, surf, base, cpos, fpos,  mrpelem, num, n) {
  num = split(mrp, mrpelem, /:/);
  if (num != 4) error("wrong mrp field");
  n = split(mrpelem[1], surf, /_/);
  num = n;
  n = split(mrpelem[2], base, /_/);
  if (n != num) error("wrong mrp field 1")
  n = split(mrpelem[3], cpos, /_/);
  if (n != num) error("wrong mrp field 2")
  n = split(mrpelem[4], fpos, /_/);
  if (n != num) error("wrong mrp field 3")
  return num;
}

# 構文解析結果の取得
# bnst[i]はi番目の文節の最後の形態素の次の形態素のID
# 文全体のheadを表す文節IDは0
function da(dep, bnst, head, type,  depelem, num, m) {
  num = split(dep, depelem, /:/);
  if (num != 3) error("wrong dep field");
  m = split(depelem[1], bnst, /_/);
  bnst[0] = 1;
  num = m;
  m = split(depelem[2], head, /_/);
  if (m != num) error("wrong dep field 1")
  m = split(depelem[3], type, /_/);
  if (m != num) error("wrong dep field 2")
  return num;
}

# 2 byte文字用index
function eucindex(s, t,  o, i) {
  o = 0;
  for (; ; ) {
    i = index(substr(s, 1 + o), t);
    if (i == 0) return 0;
    if (i % 2 == 1) break;
    o += i;
  }
  i += o;
  return i;
}

# 文字列(EUC)の出現する形態素の範囲を特定する(開始: PSTART, 終了: PEND)
# s: 文, n: 単語数, w: 単語配列, t: 探す文字列, b: 探し始める位置(byte, 0-base)
# 戻り値: 見付かった範囲の次の位置(byte, 0-base)，見付からない時は-1
function position(s, n, w, t, b,  i, j, l) {
  PSTART = -1;
  PEND = -1;

  i = eucindex(substr(s, 1 + b), t) - 1;
  if (i == -1) return -1;
  i += b;
  l = 0;
  for (j = 1; j <= n; j++) {
    l += length(w[j]);
    if (l > i) break;
  }
  PSTART = j;
  for (j++; j <= n; j++) {
    if (l >= i + length(t)) break;
    l += length(w[j]);
  }
  PEND = j - 1;
  return l;
}

# エラー処理
function error(s) {
  printf "ERROR(%s): %s\n", SCRIPT, s > "/dev/stderr";
  EXIT = 1;
  exit(1);
}

# エラー表示処理
function showError(s) {
  printf "ERROR(%s): %s", SCRIPT, s > "/dev/stderr";
}

# 辞書読み込み
function dicread(dicfile, dicw, dicp, trie_flg, trie_val,  ndic, buf, nelem, elem, s, i, r) {
  ndic = 0;
  for (; ; ) {
    r = getline buf < dicfile;
    if (r < 0) error("cannot read the dictionary");
    if (r == 0) break;
    # 辞書登録
    nelem = split(buf, elem, /\t/);
    if (nelem < 3) error("wrong dictinoary");
    dicw[ndic] = elem[1];
    dicp[ndic] = elem[2];
    # トライに登録
    s = "";
    for (i = 3; i <= nelem - 1; i++) {
      s = s "\t" elem[i];
      trie_flg[s] = 1;
    }
    s = s "\t" elem[i];
    trie_val[s] = ndic;
    ndic++;
  }
  close(dicfile);

  return ndic;
}

# 辞書のlookup
function lookup(n, w, b, e, trie_flg, trie_val, listv, listb, listl,  nlist, i, s, j, b0, e0, b1, e1) {
  nlist = 0;
  for (i = b; i <= e; i++) {
    s = "";
    for (j = 0; i + j <= e; j++) {
      s = s "\t" w[i + j];
      if (trie_val[s] != "") {
	listv[nlist] = trie_val[s];
	listb[nlist] = i;
	listl[nlist] = j;
	nlist++;
      }
      if (trie_flg[s] == "") break;
    }
  }
  # overlapする場合短いのを削除
  for (i = 0; i < nlist; i++) {
    # 開始・終了位置
    b0 = listb[i];
    e0 = listb[i] + listl[i];
    # i番めのがどれかに含まれるものならば削る
    for (j = 0; j < nlist; j++) {
      if (i == j) continue;
      b1 = listb[j];
      e1 = listb[j] + listl[j];
      if (b1 <= b0 && e0 <= e1) break;
    }
    # 削除
    if (j != nlist) {
      listv[i] = listv[nlist - 1];
      listb[i] = listb[nlist - 1];
      listl[i] = listl[nlist - 1];
      nlist--;
      i--;
    }
  }

  return nlist;
}
