Original Parser

version 1 by Ron Newcomb

  • Home page
  • Beginning
  • Previous
  • Next



  • Chapter - ScoreMatchL

    [|ScoreMatchL| scores the match list for quality in terms of what the player
    has vaguely asked for. Points are awarded for conforming with requirements
    like ``my'', and so on. Remove from the match list any entries which fail
    the basic requirements of the descriptors. (The scoring system used to
    evaluate the possibilities is discussed in detail in the DM4.)]

    To decide what number is the weight given it: (- SCORE__CHOOSEOBJ -).
    To decide what number is how much token agreement's worth : (- SCORE__IFGOOD -).
    To decide what number is how much being unconcealed's worth: (- SCORE__UNCONCEALED -).
    To decide what number is how much the best location's worth: (- SCORE__BESTLOC -).
    To decide what number is how much the second-best location's worth: (- SCORE__NEXTBESTLOC -).
    To decide what number is how much not being a direction's worth: (- SCORE__NOTCOMPASS -).
    To decide what number is how much not being scenery's worth: (- SCORE__NOTSCENERY -).
    To decide what number is how much not being the actor's worth: (- SCORE__NOTACTOR -).
    To decide what number is how much gender-animation agreement's worth: (- SCORE__GNA -).
    [To decide what number is the score divisor: (- SCORE__DIVISOR -).] [unused?]

    Use preferred held objects translates as (- Constant PREFER_HELD; -).
    Use preferred held objects.

    Include (-
    Constant SCORE__CHOOSEOBJ = 1000;
    Constant SCORE__IFGOOD = 1000; ! Changed from 500 because 1) the name was unused anyway, and 2) a naked 1000 is used in Adjudicate() for this purpose, per page 240 of the DM4. I'll use it there.
    Constant SCORE__UNCONCEALED = 100;
    Constant SCORE__BESTLOC = 60;
    Constant SCORE__NEXTBESTLOC = 40;
    Constant SCORE__NOTCOMPASS = 20;
    Constant SCORE__NOTSCENERY = 10;
    Constant SCORE__NOTACTOR = 5;
    Constant SCORE__GNA = 1;
    !Constant SCORE__DIVISOR = 20;
    -).

    To rank the remaining according to their properties and descriptor words used and their location regarding (context - a grammar token) (this is ScoreMatchL):
        [ First rule about creating a noun filter based on what descriptor words the player typed in: initialize minimum required score. ]
        let the threshold be zero;
        [ A rule about MY, HIS, HER, THEIR, etc. ]
        if the type of descriptor word used includes a possessive descriptor, increment threshold;
        [ A rule about THAT as in THAT BOX ]
        if the type of descriptor word used includes a THAT descriptor, increment threshold; [as in "that box"]
        [ A rule about LIT/LIGHTED things ]
        if the type of descriptor word used includes a lit descriptor, increment threshold;
        [ A rule about UNLIT/UNLIGHTED things ]
        if the type of descriptor word used includes an unlit descriptor, increment threshold;
        [ A rule about pronouns that are set to a noun should have a say in disallowing nouns. ]
        unless what the pronoun stands for is nothing, increment threshold;
        [ end rulebook ]
        if trace 4, say " Scoring match list: indef mode [the indefinite article mode as a debugging number] type [the type of descriptor word used as a debugging number], satisfying [threshold] requirements:[line break][run paragraph on]";
        [ This paragraph of code exists only because of the "use preferred held objects" option. ]
        let how much being in the actor's pocket's worth be how much the best location's worth;
        let how much being in the actor's room's worth be how much the second-best location's worth;
        if the preferred held objects option is active:
            if the action to be is either the taking action or the removing it from action: [then swap them]
                now how much being in the actor's pocket's worth is how much the second-best location's worth;
                now how much being in the actor's room's worth is how much the best location's worth;
        otherwise:
            unless the context is either 'something preferably held' or 'things preferably held' or 'other things':[then swap them]
                now how much being in the actor's pocket's worth is how much the second-best location's worth;
                now how much being in the actor's room's worth is how much the best location's worth;
        repeat through the match list of size the number of objects in the match list:
            [ First excluding rule initializes variables. ]
            let its owner be the parent of the chosen element;
            let its score be 0;
            [ A excluding rule about MY ]
            if the type of descriptor word used includes a possessive descriptor and its owner is the person asked, increment its score;
            [ A excluding rule about THAT as in THAT BOX ]
            if the type of descriptor word used includes a THAT descriptor and its owner is the actor's scopewise location, increment its score;
            [ A excluding rule about the LIT/LIGHTED property ]
            if the type of descriptor word used includes a lit descriptor and the chosen element provides the property lit directly, increment its score;
            [ A excluding rule about the UNLIT/UNLIGHTED property ]
            if the type of descriptor word used includes an unlit descriptor and the chosen element does not provide the property lit directly, increment its score;
            [ A excluding rule about things which a pronoun refers to ]
            if its owner is what the pronoun stands for and its owner is not nothing, increment its score;
            [ end rulebook ]
            if its score is less than the threshold:
                if trace 4, say " [The chosen element] ([the chosen element as a debugging number]) in [the its owner] is rejected (doesn't match descriptors)[line break]";
                change the chosen element of the match list to the used-up object;
            otherwise:
                [ First ranking rule: invoke the DOES THE PLAYER MEAN rules (usually) and initialize the score. ]
                now its score is the weight given it multiplied by how much does the player mean the chosen element;
                [ A rule about the undescribed/concealed property ]
                if the chosen element does not provide the property undescribed directly:
                    increase its score by how much being unconcealed's worth;
                [ A rule about the liklihood given its location ]
                if its owner is the person asked:
                    increase its score by how much being in the actor's pocket's worth;
                otherwise if its owner is the actor's scopewise location:
                    increase its score by how much being in the actor's room's worth;
                otherwise if its owner is not the compass:
                    increase its score by how much not being a direction's worth;
                [ A rule about the scenery property ]
                if the chosen element does not provide the property scenery directly:
                    increase its score by how much not being scenery's worth;
                [ A rule about preferring actions on things other than yourself ]
                if the chosen element is not the person asked:
                    increase its score by how much not being the actor's worth;
                [ A rule about the his/her/it/they/that/those words implying certain things ]
                if the grammatical case includes any of the gender-animation usages for the chosen element:
                    increase its score by how much gender-animation agreement's worth;
                [ end rulebook ]
                change the match score list element to its score + the match score list element;
                if trace 4, say " [The chosen element] ([the chosen element as a debugging number]) in [the its owner] : [the match score list element] points[line break]";
        [ Now shorten the list by removing all entries which are "the used-up object". ]
        while the number of objects in the match list is at least one:
            if the used-up object is listed in the match list of size the number of objects in the match list:
                shift the match list left between the chosen and the number of objects in the match list using a scratchpad;
                shift the match score list left between the chosen and the number of objects in the match list using scratchspace;
                decrement the number of objects in the match list;
            otherwise:
                stop.


    [ ScoreMatchL context its_owner its_score obj i j threshold met a_s l_s;
    ! if (indef_type & OTHER_BIT ~= 0) threshold++;
    if (indef_type & MY_BIT ~= 0) threshold++;
    if (indef_type & THAT_BIT ~= 0) threshold++;
    if (indef_type & LIT_BIT ~= 0) threshold++;
    if (indef_type & UNLIT_BIT ~= 0) threshold++;
    if (indef_owner ~= nothing) threshold++;

    #Ifdef DEBUG;
    if (parser_trace >= 4) print " Scoring match list: indef mode ", indef_mode, " type ",
    indef_type, ", satisfying ", threshold, " requirements:^";
    #Endif; ! DEBUG

    #ifdef PREFER_HELD;
    a_s = SCORE__BESTLOC; l_s = SCORE__NEXTBESTLOC;
    if (action_to_be == ##Take or ##Remove) {
    a_s = SCORE__NEXTBESTLOC; l_s = SCORE__BESTLOC;
    }
    context = context; ! silence warning
    #ifnot;
    a_s = SCORE__NEXTBESTLOC; l_s = SCORE__BESTLOC;
    if (context == HELD_TOKEN or MULTIHELD_TOKEN or MULTIEXCEPT_TOKEN) {
    a_s = SCORE__BESTLOC; l_s = SCORE__NEXTBESTLOC;
    }
    #endif; ! PREFER_HELD

    for (i=0 : i<number_matched : i++) {
    obj = match_list-->i; its_owner = parent(obj); its_score=0; met=0;

    ! if (indef_type & OTHER_BIT ~= 0
    ! && obj ~= itobj or himobj or herobj) met++;
    if (indef_type & MY_BIT ~= 0 && its_owner == actor) met++;
    if (indef_type & THAT_BIT ~= 0 && its_owner == actors_location) met++;
    if (indef_type & LIT_BIT ~= 0 && obj has light) met++;
    if (indef_type & UNLIT_BIT ~= 0 && obj hasnt light) met++;
    if (indef_owner ~= 0 && its_owner == indef_owner) met++;

    if (met < threshold) {
    #Ifdef DEBUG;
    if (parser_trace >= 4)
    print " ", (The) match_list-->i, " (", match_list-->i, ") in ",
    (the) its_owner, " is rejected (doesn't match descriptors)^";
    #Endif; ! DEBUG
    match_list-->i = -1;
    }
    else {
    its_score = 0;
    if (obj hasnt concealed) its_score = SCORE__UNCONCEALED;

    if (its_owner == actor) its_score = its_score + a_s;
    else
    if (its_owner == actors_location) its_score = its_score + l_s;
    else
    if (its_owner ~= compass) its_score = its_score + SCORE__NOTCOMPASS;

    its_score = its_score + SCORE__CHOOSEOBJ * ChooseObjects(obj, 2);

    if (obj hasnt scenery) its_score = its_score + SCORE__NOTSCENERY;
    if (obj ~= actor) its_score = its_score + SCORE__NOTACTOR;

    ! A small bonus for having the correct GNA,
    ! for sorting out ambiguous articles and the like.

    if (indef_cases & (PowersOfTwo_TB-->(GetGNAOfObject(obj))))
    its_score = its_score + SCORE__GNA;

    match_scores-->i = match_scores-->i + its_score;
    #Ifdef DEBUG;
    if (parser_trace >= 4) print " ", (The) match_list-->i, " (", match_list-->i,
    ") in ", (the) its_owner, " : ", match_scores-->i, " points^";
    #Endif; ! DEBUG
    }
    }

    for (i=0 : i<number_matched : i++) {
    while (match_list-->i == -1) {
    if (i == number_matched-1) { number_matched--; break; }
    for (j=i : j<number_matched-1 : j++) {
    match_list-->j = match_list-->(j+1);
    match_scores-->j = match_scores-->(j+1);
    }
    number_matched--;
    }
    }
    ]