Menu

how to check LF

Help
2007-12-19
2013-04-08
  • Multimodal parsing

    In an application, multiple strings can trigger an identical task.
    For example, both "hello ken" and "Good morning Ken" can cause the animator "ken" to say "Nice to meet you".

    After the semantic information (semLF) is derived, only a part of the information need to be checked to triger a task.

    the first method can be:
    create a LF (triggerLF) with only the information which is necessary to trigger a task. then unify semLF with triggerLF,
    if success, then trigger the task.

    the second method can be:
    if(semLF.getVal1().equals(...) &&  semLF.getVal2().equals(...) && ...)

    ----------------------------------------------------------------------------------
    According to the API of openCCG, "Unification is not attempted for Ops.", is there anyway to implement the first method based on openCCG, or we can only use the second method?

    Thanks,
    Yong

     
    • Michael White

      Michael White - 2007-12-19

      Good question!

      There is actually some code you could borrow from in order to implement a solution somewhere in between.  What you're interested in is related to the instantiation of LFs from lexical categories against an input LF in realization.  So have a look at the code in the EdgeFactory.instantiate(Category cat, Category cat2, int predIndex):List<Pair<Substitution,BitSet>> method in the opennlp.ccg.realize package.

      It might be worth considering trying to migrate this functionality to the hylo package, but it's not clear to me what the requirements should be in general.  In the realizer, we're interested in multiple possible instantiations against a flat LF, with no restriction on where the instantiation occurs (ie not nec at the root), and with bit vectors set according to what's instantiated.  There's also some indexing to make this efficient, but I don't think we'd want to incur this overhead whenever we create an Op.

      -Mike

       
    • Multimodal parsing

      Merry Xmas, Mike!

      To continue my issue, I decide to check if "triggerLF" subsumes "semLF" by the following code.
      The idea is checking if every pred in triggerLF can unify with a pred in semLF. the problem I found is
      ------------------------------------------------
      1. "@A_0:action(<Patient>B_0:sem-obj)" unifies "@E_3:action(<Patient>Y_3:sem-obj)"
         and
      2. "@B_0:animate-being(sakura)" unifies "@X_3:animate-being(sakura)"
      ------------------------------------------------
      actually, in (1) it is Y_3, but it is X_3 in (2)

      any suggestion? thanks

          private boolean subsume(Op superOp, Op subOp)
          {
              if(!superOp.getName().equals(subOp.getName())) return false;
             
              List<SatOp> superPreds = HyloHelper.getPreds(superOp);
              List<SatOp> subPreds = HyloHelper.getPreds(subOp);
             
              Substitution subst = null;
              boolean unifyFlag = false;

              for(int i=0; i < superPreds.size(); i++)
              {
                  LF superPred = superPreds.get(i);
                  unifyFlag = false;
                  for (int j=0; j < subPreds.size(); j++) {
                      LF subPred = subPreds.get(j);
                      subst = new SimpleSubstitution();
                      try {
                          Unifier.unify(superPred, subPred, subst);
                          unifyFlag = true;
                          break;
                      } catch (UnifyFailure uf) {}
                  }
                  if(!unifyFlag) break;
              }
              return unifyFlag;
          }

       
      • Michael White

        Michael White - 2007-12-26

        I'm not sure I understand the problem, but I Suspect you will need to propagate successful unifications by filling the substitutions.

        It may help for you to do some background reading on unification in a textbook.

         
    • Multimodal parsing

      Let me explain in another way.
      To check if
      1. (@A_0:action(hello) ^ @A_0:action(<Patient>B_0:sem-obj) ^ @B_0:sem-obj(sakura))
      unifies
      2. (@E_1:action(hello) ^ @E_1:action(<Actor>X_1:animate-being) ^ @E_1:action(<Patient>Y_1:sem-obj) ^ @X_1:animate-being(sakura))

      I check if
      (@A_0:action(hello) unifies (@E_1:action(hello)
      and @A_0:action(<Patient>B_0:sem-obj) unifies @E_1:action(<Patient>Y_1:sem-obj)
      and @B_0:sem-obj(sakura)) unifies @X_1:animate-being(sakura))

      Yes, they are all true. So I conclude 1 unifies 2 which is not true.
      Because
      in 1. it is @A_0:action(<Patient>B_0:sem-obj) ^ @B_0:sem-obj(sakura))
                                      =====           =====
      but in 2. the Satops unified are @E_1:action(<Patient>Y_1:sem-obj) ^ @X_1:animate-being(sakura))
                                       =====                               =====

      is it clear this time?
      thanks,
      Yong

       
      • Michael White

        Michael White - 2007-12-26

        Yes, that's what I thought.  Unification requires simultaneous substitutions, not independent ones.  Additionally, you'll want to avoid unifying eg X_1 and Y_1; converting nominal vars to atoms after parsing will help with this (there's a HyloHelper method for doing so).

        It might help to read the chapter on unification in Jurafsky and Martin's textbook (http://www.cs.colorado.edu/~martin/slp2.html) or some other one, as a better understanding of unification will help you to write code that works.

         

Log in to post a comment.