'2017/06/09'에 해당되는 글 2건

  1. 2017.06.09 [Arirang Analyzer - lucene 6.5.0] Term startOffset 정렬 오류
  2. 2017.06.09 [Arirang] first position increment must be > 0 오류

[Arirang Analyzer - lucene 6.5.0] Term startOffset 정렬 오류

ITWeb/검색일반 2017. 6. 9. 10:23

[arirang-analyzer-6.5.0]

  term analyzed 시 startOffset 정보에 대한 정렬이 역전 되는 오류

  개별 term 에서의 startOffset 이 역전 되기 때문에 아래 class 의 method 에서 정렬을 다시 맞춰줍니다.

  (정상적인 방법 이라기 보다는 일단 문제를 회피하기 위한 방법 입니다.)


  Class : KoreanFilter

  Method 1 :

    private void analysisKorean(String input) throws MorphException {


  //  input = trimHangul(input);

      List<AnalysisOutput> outputs = morph.analyze(input);

      if (outputs.size() == 0) {

        return;

      }


      Map<String, KoreanToken> map = new LinkedHashMap<String, KoreanToken>();

      if (hasOrigin) {

        map.put("0:" + input, new KoreanToken(input, offsetAtt.startOffset()));

      }


      extractKeyword(outputs, offsetAtt.startOffset(), map, 0);


      Collection<KoreanToken> values = map.values();

      for (KoreanToken kt : values) {

        kt.setOutputs(outputs);

      }


      // 이 부분에서 map 에 등록된 정보를 정렬 합니다.


      morphQueue.addAll(map.values());

    }


  Method 2 :

    private void analysisKorean(String input) throws MorphException {


  //  input = trimHangul(input);

      List<AnalysisOutput> outputs = morph.analyze(input);

      if (outputs.size() == 0) {

        return;

      }


      Map<String, KoreanToken> map = new LinkedHashMap<String, KoreanToken>();

      if (hasOrigin) {

        map.put("0:" + input, new KoreanToken(input, offsetAtt.startOffset()));

      }


      extractKeyword(outputs, offsetAtt.startOffset(), map, 0);


      Collection<KoreanToken> values = map.values();

      for (KoreanToken kt : values) {

        kt.setOutputs(outputs);

      }


      morphQueue.addAll(map.values());

      // 이 부분에서 morphQueue 에 등록된 정보를 정렬 합니다.

      morphQueue.sort(Comparator.comparingInt(KoreanToken::getOffset));

    }


  Method 3 : 

    protected void extractKeyword(List<AnalysisOutput> outputs, int startoffset,

      final Map<String, KoreanToken> map, int position) {

      ... 원본 코드 생략


      // 이 부분에서 map 에 대한 등록된 정보를 정렬 합니다.

    }


  정렬 방법 :

    참고) https://stackoverflow.com/questions/109383/sort-a-mapkey-value-by-values-java


    final List<Map.Entry<String, KoreanToken>> offsetSorts = map.entrySet().stream()

        .sorted(Map.Entry.comparingByValue(Comparator.comparingInt(KoreanToken::getOffset)))

        .collect(Collectors.toList());


    map.clear();


    offsetSorts.stream().forEachOrdered(e -> map.put(e.getKey(), e.getValue()));


  Method 4 :

    KoreanFilter 를 상속받아 CustomKoreanFilter 를 만들어 사용 하면 됩니다.


:

[Arirang] first position increment must be > 0 오류

ITWeb/검색일반 2017. 6. 9. 10:22

아직 확인 및 테스트 하지 않았습니다. ^^;

그냥 코드만 보고 이렇게 하면 되겠다 정도만 입니다.


- DefaultIndexingChain.java

first position increment must be > 0


관련 에러 수정을 위해서는 KoreanFilter.java 내 posIncrAtt.setPositionIncrement(iw.getPosInc()); 영역에서 

iw.getPosInc() 가 -1 인지 검사해서 1로 변경을 해줍니다.

변경에 따른 오류에 대해서 검토가 필요 합니다.


  private void setAttributesFromQueue(boolean isFirst) {

    final KoreanToken iw = morphQueue.removeFirst();

    if (isFirst && !morphQueue.isEmpty()) {

      // our queue has more elements remaining (e.g. we decompounded)

      // capture state for those. We set the term attribute to be empty

      // so we save lots of array copying later.

      termAtt.setEmpty();

      currentState = captureState();

    }

 

    termAtt.setEmpty().append(iw.getTerm());

    offsetAtt.setOffset(iw.getOffset(), iw.getOffset() + iw.getLength());

    morphAtt.setToken(iw);


    // on the first Token we preserve incoming increment:

    if (!isFirst) {

      posIncrAtt.setPositionIncrement(iw.getPosInc());

    }

    

    String type = TokenUtilities.getType(iw.getTerm().toCharArray(), iw.getTerm().length());

    typeAtt.setType(type);

    

    // TODO: How to handle PositionLengthAttribute correctly?

  }



: