Annotation of researchv10no/games/wump.c, revision 1.1.1.1

1.1       root        1: #
                      2: 
                      3: /*
                      4:  *     wumpus
                      5:  *     stolen from PCC Vol 2 No 1
                      6:  */
                      7: 
                      8: #define        NBAT    3
                      9: #define        NROOM   20
                     10: #define        NTUNN   3
                     11: #define        NPIT    3
                     12: 
                     13: struct room
                     14: {
                     15:        int     tunn[NTUNN];
                     16:        int     flag;
                     17: } room[NROOM];
                     18: 
                     19: char   *intro[] =
                     20: {
                     21:        "\n",
                     22:        "Welcome to 'Hunt the Wumpus.'\n",
                     23:        "\n",
                     24:        "The Wumpus lives in a cave of %d rooms.\n",
                     25:        "Each room has %d tunnels leading to other rooms.\n",
                     26:        "\n",
                     27:        "Hazards:\n",
                     28:        "\n",
                     29:        "Bottomless Pits - Some rooms have Bottomless Pits in them.\n",
                     30:        "       If you go there, you fall into the pit and lose!\n",
                     31:        "Super Bats - Some other rooms have super bats.\n",
                     32:        "       If you go there, a bat will grab you and take you to\n",
                     33:        "       somewhere else in the cave where you could\n",
                     34:        "       fall into a pit or run into the . . .\n",
                     35:        "\n",
                     36:        "Wumpus:\n",
                     37:        "\n",
                     38:        "The Wumpus is not bothered by the hazards since\n",
                     39:        "he has sucker feet and is too big for a bat to lift.\n",
                     40:        "\n",
                     41:        "Usually he is asleep.\n",
                     42:        "Two things wake him up:\n",
                     43:        "       your entering his room\n",
                     44:        "       your shooting an arrow anywhere in the cave.\n",
                     45:        "If the wumpus wakes, he either decides to move one room or\n",
                     46:        "stay where he was.  But if he ends up where you are,\n",
                     47:        "he eats you up and you lose!\n",
                     48:        "\n",
                     49:        "You:\n",
                     50:        "\n",
                     51:        "Each turn you may either move or shoot a crooked arrow.\n",
                     52:        "\n",
                     53:        "Moving - You can move to one of the adjoining rooms;\n",
                     54:        "       that is, to one that has a tunnel connecting it with\n",
                     55:        "       the room you are in.\n",
                     56:        "\n",
                     57:        "Shooting - You have 5 arrows.  You lose when you run out.\n",
                     58:        "       Each arrow can go from 1 to 5 rooms.\n",
                     59:        "       You aim by telling the computer\n",
                     60:        "       The arrow's path is a list of room numbers\n",
                     61:        "       telling the arrow which room to go to next.\n",
                     62:        "       The list is terminated with a 0.\n",
                     63:        "       The first room in the path must be connected to the\n",
                     64:        "       room you are in.  Each succeeding room must be\n",
                     65:        "       connected to the previous room.\n",
                     66:        "       If there is no tunnel between two of the rooms\n",
                     67:        "       in the arrow's path, the arrow chooses one of the\n",
                     68:        "       three tunnels from the room it's in and goes its\n",
                     69:        "       own way.\n",
                     70:        "\n",
                     71:        "       If the arrow hits the wumpus, you win!\n",
                     72:        "       If the arrow hits you, you lose!\n",
                     73:        "\n",
                     74:        "Warnings:\n",
                     75:        "\n",
                     76:        "When you are one or two rooms away from the wumpus,\n",
                     77:        "the computer says:\n",
                     78:        "               'I smell a Wumpus'\n",
                     79:        "When you are one room away from some other hazard, it says:\n",
                     80:        "               Bat    - 'Bats nearby'\n",
                     81:        "               Pit    - 'I feel a draft'\n",
                     82:        "\n",
                     83:        0,
                     84: };
                     85: 
                     86: #define        BAT     01
                     87: #define        PIT     02
                     88: #define        WUMP    04
                     89: 
                     90: int    arrow;
                     91: int    loc;
                     92: int    wloc;
                     93: int    tchar;
                     94: 
                     95: main()
                     96: {
                     97:        register i, j;
                     98:        register struct room *p;
                     99:        int k, icomp();
                    100: 
                    101:        printf("Instructions? (y-n) ");
                    102:        if(rline() == 'y')
                    103:                for(i=0; intro[i]; i++)
                    104:                        printf(intro[i], i&1? NROOM: NTUNN);
                    105: 
                    106: 
                    107: /*
                    108:  * initialize the room connections
                    109:  */
                    110: 
                    111: init:
                    112:        p = &room[0];
                    113:        for(i=0; i<NROOM; i++) {
                    114:                for(j=0; j<NTUNN; j++)
                    115:                        p->tunn[j] = -1;
                    116:                p++;
                    117:        }
                    118:        k = 0;
                    119:        for(i=1; i<NROOM; ) {
                    120:                j = rnum(NROOM);
                    121:                p = &room[j];
                    122:                if(j == k || p->tunn[0] >= 0 || p->tunn[1] >= 0)
                    123:                        continue;
                    124:                p->tunn[1] = k;
                    125:                room[k].tunn[0] = j;
                    126:                k = j;
                    127:                i++;
                    128:        }
                    129:        p = &room[0];
                    130:        for(i=0; i<NROOM; i++) {
                    131:                for(j=0; j<NTUNN; j++) {
                    132:                        if(p->tunn[j] < 0)
                    133:                                p->tunn[j] = tunnel(i);
                    134:                        if(p->tunn[j] == i)
                    135:                                goto init;
                    136:                        for(k=0; k<j; k++)
                    137:                                if(p->tunn[j] == p->tunn[k])
                    138:                                        goto init;
                    139:                }
                    140:                qsort(&p->tunn[0], NTUNN, sizeof(int), icomp);
                    141:                p++;
                    142:        }
                    143: 
                    144: /*
                    145:  * put in player, wumpus,
                    146:  * pits and bats
                    147:  */
                    148: 
                    149: setup:
                    150:        arrow = 5;
                    151:        p = &room[0];
                    152:        for(i=0; i<NROOM; i++) {
                    153:                p->flag = 0;
                    154:                p++;
                    155:        }
                    156:        for(i=0; i<NPIT; ) {
                    157:                p = &room[rnum(NROOM)];
                    158:                if((p->flag&PIT) == 0) {
                    159:                        p->flag |= PIT;
                    160:                        i++;
                    161:                }
                    162:        }
                    163:        for(i=0; i<NBAT; ) {
                    164:                p = &room[rnum(NROOM)];
                    165:                if((p->flag&(PIT|BAT)) == 0) {
                    166:                        p->flag |= BAT;
                    167:                        i++;
                    168:                }
                    169:        }
                    170:        i = rnum(NROOM);
                    171:        wloc = i;
                    172:        room[i].flag |= WUMP;
                    173:        for(;;) {
                    174:                i = rnum(NROOM);
                    175:                if((room[i].flag&(PIT|BAT|WUMP)) == 0) {
                    176:                        loc = i;
                    177:                        break;
                    178:                }
                    179:        }
                    180: 
                    181: /*
                    182:  *     main loop of the game
                    183:  */
                    184: 
                    185: loop:
                    186:        printf("You are in room %d\n", loc+1);
                    187:        p = &room[loc];
                    188:        if(p->flag&PIT) {
                    189:                printf("You fell into a pit\n");
                    190:                goto done;
                    191:        }
                    192:        if(p->flag&WUMP) {
                    193:                printf("You were eaten by the wumpus\n");
                    194:                goto done;
                    195:        }
                    196:        if(p->flag&BAT) {
                    197:                printf("There's a bat in your room\n");
                    198:                loc = rnum(NROOM);
                    199:                goto loop;
                    200:        }
                    201:        for(i=0; i<NTUNN; i++)
                    202:        if(near(&room[p->tunn[i]], WUMP))
                    203:                goto nearwump;
                    204:        if (near(p, WUMP)) {
                    205:        nearwump:
                    206:                printf("I smell a wumpus\n");
                    207:        }
                    208:        if (near(p, BAT))
                    209:                printf("Bats nearby\n");
                    210:        if (near(p, PIT))
                    211:                printf("I feel a draft\n");
                    212:        printf("There are tunnels to");
                    213:        for(i=0; i<NTUNN; i++)
                    214:                printf(" %d", p->tunn[i]+1);
                    215:        printf("\n");
                    216: 
                    217: again:
                    218:        printf("Move or shoot (m-s) ");
                    219:        switch(rline()) {
                    220:        case 'm':
                    221:                if(tchar == '\n')
                    222:                        printf("which room? ");
                    223:                i = rin()-1;
                    224:                for(j=0; j<NTUNN; j++)
                    225:                        if(i == p->tunn[j])
                    226:                                goto groom;
                    227:                printf("You hit the wall\n");
                    228:                goto again;
                    229:        groom:
                    230:                loc = i;
                    231:                if(i == wloc)
                    232:                        goto mwump;
                    233:                goto loop;
                    234: 
                    235:        case 's':
                    236:                if(tchar == '\n')
                    237:                        printf("Give list of rooms terminated by 0\n");
                    238:                for(i=0; i<5; i++) {
                    239:                        j = rin()-1;
                    240:                        if(j == -1)
                    241:                                break;
                    242:                ranarw:
                    243:                        for(k=0; k<NTUNN; k++)
                    244:                                if(j == p->tunn[k])
                    245:                                        goto garow;
                    246:                        j = rnum(NROOM);
                    247:                        goto ranarw;
                    248:                garow:
                    249:                        p = &room[j];
                    250:                        if(j == loc) {
                    251:                                printf("You shot yourself\n");
                    252:                                goto done;
                    253:                        }
                    254:                        if(p->flag&WUMP) {
                    255:                                printf("You slew the wumpus\n");
                    256:                                goto done;
                    257:                        }
                    258:                }
                    259:                if(--arrow == 0) {
                    260:                        printf("That was your last shot\n");
                    261:                        goto done;
                    262:                }
                    263:                goto mwump;
                    264:        }
                    265: 
                    266:        goto again;
                    267: 
                    268: mwump:
                    269:        p = &room[wloc];
                    270:        p->flag &= ~WUMP;
                    271:        i = rnum(NTUNN+1);
                    272:        if(i != NTUNN)
                    273:                wloc = p->tunn[i];
                    274:        room[wloc].flag |= WUMP;
                    275:        goto loop;
                    276: 
                    277: done:
                    278:        printf("Another game? (y-n) ");
                    279:        if(rline() == 'y') {
                    280:                printf("Same room setup? (y-n) ");
                    281:                if(rline() == 'y')
                    282:                        goto setup;
                    283:                goto init;
                    284:        }
                    285: }
                    286: 
                    287: tunnel(i)
                    288: {
                    289:        register struct room *p;
                    290:        register n, j;
                    291:        int c;
                    292: 
                    293:        c = 20;
                    294: 
                    295: loop:
                    296:        n = rnum(NROOM);
                    297:        if(n == i)
                    298:                if(--c > 0)
                    299:                        goto loop;
                    300:        p = &room[n];
                    301:        for(j=0; j<NTUNN; j++)
                    302:        if(p->tunn[j] == -1) {
                    303:                p->tunn[j] = i;
                    304:                return(n);
                    305:        }
                    306:        goto loop;
                    307: }
                    308: 
                    309: rline()
                    310: {
                    311:        register char c, r;
                    312: 
                    313:        while((c=getchar()) == ' ');
                    314:        r = c;
                    315:        while(c != '\n' && c != ' ') {
                    316:                if(c == '\0')
                    317:                        exit();
                    318:                c = getchar();
                    319:        }
                    320:        tchar = c;
                    321:        return(r);
                    322: }
                    323: 
                    324: rnum(n)
                    325: {
                    326:        static long first;
                    327: 
                    328:        if(first==0) {
                    329:                time(&first);
                    330:                srand((int)first);
                    331:        }
                    332:        return((rand()/32768.0) * n);
                    333: }
                    334: 
                    335: rin()
                    336: {
                    337:        register n, c;
                    338: 
                    339:        n = 0;
                    340:        c = getchar();
                    341:        while(c != '\n' && c != ' ') {
                    342:                if(c<'0' || c>'9') {
                    343:                        while(c != '\n') {
                    344:                                if(c == 0)
                    345:                                        exit();
                    346:                                c = getchar();
                    347:                        }
                    348:                        return(0);
                    349:                }
                    350:                n = n*10 + c-'0';
                    351:                c = getchar();
                    352:        }
                    353:        return(n);
                    354: }
                    355: 
                    356: near(ap, ahaz)
                    357: struct room *ap;
                    358: {
                    359:        register struct room *p;
                    360:        register haz, i;
                    361: 
                    362:        p = ap;
                    363:        haz = ahaz;
                    364:        for(i=0; i<NTUNN; i++)
                    365:        if(room[p->tunn[i]].flag & haz)
                    366:                return (1);
                    367:        return(0);
                    368: }
                    369: 
                    370: icomp(p1, p2)
                    371: int *p1, *p2;
                    372: {
                    373: 
                    374:        return(*p1 - *p2);
                    375: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.