Вопрос

I have created two different .pl files in SWI-Prolog for a text adventure game. They are two different missions.

Is there any way at the end of the first mission to open the second mission (the second .pl file) and close the first one?

Also, what would be better: To create N .pl files for my N missions or one big .pl file?

Это было полезно?

Решение

I agree with your initial impulse in thinking that using a number of module files would be best. I imagine that one reason for using different files would be to provide different name spaces for facts and rules which would be best expressed using the same predicates. So that, for instance, Description would be different for room(1, Description) in mission 1 than in mission 2.

One way of achieving this would be by accessing private, non-exported predicates in each of the different mission-modules. (Aside: I read Jan Wielemaker caution against this practice somewhere, but I'm not sure why, nor am I sure that I did read this.)

Here's a possible pattern I threw together:

Given a main file, 'game.pl', with the following program,

:- use_module([mission1, mission2]).

start :-
    playing(mission1).

playing(CurrentMission) :-
    read(Command),
    command(CurrentMission, Command),
    playing(CurrentMission).

command(_, quit) :- write('Good bye.'), halt.
command(CurrentMission, Command) :-
    ( current_predicate(CurrentMission:Command/_)  % Makes sure Command is defined in the module.
    ->  CurrentMission:Command                     % Call Command in the current mission-module
    ;   write('You can\'t do that.'),              % In case Command isn't defined in the mission.
    ).

and these mission modules,

In file 'mission1.pl':

:- module(mission1, []).

turn_left :-
    write('You see a left-over turnip').

eat_turnip :-
    write('You are transported to mission2'),
    playing(mission2).                         % Return to the prompt in `game` module, but with the next module.

In file 'mission2.pl':

:- module(mission2, []).

turn_left :-
    write('You see a left-leaning turncoat.').

Then we can play this shitty game:

?- start.
|: turn_left.
You see a left-over turnip
|: eat_turnip.
You are transported to mission2
|: turn_left.
You see a left-leaning turncoat.
|: quit
|: .
Good bye.

The specifics of this program are problematic for a number of reasons. For instance, I expect we might rather have a single predicate that handles navigating through places, and that we'd rather describe places and object that react to different commands in our missions, rather than account for every possible command. But the general principle of using the different files would still work.

Another approach would be to use consult/1 and unload_file/1 to load and unload modules, in which case you should be able to use their public, exported predicates instead of calling them by module. Documentation for those and related predicates can be found in the manual in the section "Loading Prolog Source Files".

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top