mirror of
https://github.com/Mercury-Language/mercury.git
synced 2026-04-15 09:23:44 +00:00
255 lines
7.5 KiB
Mathematica
255 lines
7.5 KiB
Mathematica
%---------------------------------------------------------------------------%
|
|
% vim: ft=mercury ts=4 sw=4 et
|
|
%---------------------------------------------------------------------------%
|
|
% Copyright (C) 1997-2003, 2005-2006, 2012 The University of Melbourne.
|
|
% Copyright (C) 2014-2016, 2018, 2020-2022, 2024, 2026 The Mercury team.
|
|
% This file is distributed under the terms specified in COPYING.LIB.
|
|
%---------------------------------------------------------------------------%
|
|
%
|
|
% File: prolog.m.
|
|
% Main author: fjh.
|
|
% Stability: high.
|
|
%
|
|
% This file contains predicates that are intended to help people
|
|
% porting Prolog programs, or writing programs in the intersection
|
|
% of Mercury and Prolog.
|
|
%
|
|
%---------------------------------------------------------------------------%
|
|
%---------------------------------------------------------------------------%
|
|
|
|
:- module prolog.
|
|
:- interface.
|
|
|
|
:- import_module io.
|
|
:- import_module list.
|
|
:- import_module pair.
|
|
:- import_module univ.
|
|
|
|
%---------------------------------------------------------------------------%
|
|
%
|
|
% Prolog arithmetic operators.
|
|
%
|
|
|
|
:- pred T =:= T. % In Mercury, just use =
|
|
:- mode in =:= in is semidet.
|
|
|
|
:- pred T =\= T. % In Mercury, just use \=
|
|
:- mode in =\= in is semidet.
|
|
|
|
%---------------------------------------------------------------------------%
|
|
%
|
|
% Prolog term comparison operators.
|
|
%
|
|
|
|
:- pred T == T. % In Mercury, just use =
|
|
:- mode in == in is semidet.
|
|
|
|
:- pred T \== T. % In Mercury, just use \=
|
|
:- mode in \== in is semidet.
|
|
|
|
% Prolog's so-called "univ" operator, `=..'.
|
|
% Note: this is not related to Mercury's "univ" type!
|
|
% In Mercury, use `deconstruct.deconstruct' instead.
|
|
|
|
:- pred T =.. univ_result.
|
|
:- mode in =.. out is det.
|
|
|
|
% Note that the Mercury =.. is a bit different to the Prolog one.
|
|
% We could make it slightly more similar by overloading '.'/2,
|
|
% but that would cause ambiguities that might prevent type
|
|
% inference in a lot of cases.
|
|
%
|
|
% :- type univ_result ---> '.'(string, list(univ)).
|
|
:- type univ_result == pair(string, list(univ)).
|
|
|
|
% arg/3.
|
|
% In Mercury, use arg/4 (defined in module deconstruct) instead:
|
|
%
|
|
% arg(ArgNum, Term, Data) :-
|
|
% deconstruct.arg(Term, canonicalize, ArgNum - 1, Data).
|
|
%
|
|
:- pred arg(int::in, T::in, univ::out) is semidet.
|
|
|
|
% det_arg/3: like arg/3, but calls error/1 rather than failing
|
|
% if the index is out of range.
|
|
%
|
|
:- pred det_arg(int::in, T::in, univ::out) is det.
|
|
|
|
%---------------------------------------------------------------------------%
|
|
%
|
|
% Prolog-style predicates for opening and switching streams.
|
|
%
|
|
|
|
% see(FileName, Result, !IO):
|
|
% Attempts to open the named file for input and, if successful,
|
|
% sets the current input stream to the newly opened stream.
|
|
% Result is either 'ok' or 'error(ErrorCode)'.
|
|
%
|
|
:- pred see(string::in, io.res::out, io::di, io::uo) is det.
|
|
|
|
% Attempts to open a file for binary input and, if successful, sets
|
|
% the current binary input stream to the newly opened stream.
|
|
% Result is either 'ok' or 'error(ErrorCode)'.
|
|
%
|
|
:- pred see_binary(string::in, io.res::out, io::di, io::uo) is det.
|
|
|
|
%---------------------%
|
|
|
|
% seen(!IO):
|
|
% Closes the current input stream.
|
|
% The current input stream reverts to standard input.
|
|
% This will throw an io.error exception if an I/O error occurs.
|
|
%
|
|
:- pred seen(io::di, io::uo) is det.
|
|
|
|
% Closes the current binary input stream.
|
|
% The current binary input stream reverts to standard input.
|
|
% This will throw an io.error exception if an I/O error occurs.
|
|
%
|
|
:- pred seen_binary(io::di, io::uo) is det.
|
|
|
|
%---------------------%
|
|
|
|
% tell(FileName, Result, !IO):
|
|
% Attempts to open the named file for output, and if successful,
|
|
% sets the current output stream to the newly opened stream.
|
|
% Result is either 'ok' or 'error(ErrorCode)'.
|
|
%
|
|
:- pred tell(string::in, io.res::out, io::di, io::uo) is det.
|
|
|
|
% Attempts to open a file for binary output, and if successful sets
|
|
% the current binary output stream to the newly opened stream.
|
|
% As per Prolog tell/1. Result is either 'ok' or 'error(ErrorCode)'.
|
|
%
|
|
:- pred tell_binary(string::in, io.res::out, io::di, io::uo) is det.
|
|
|
|
%---------------------%
|
|
|
|
% told(!IO):
|
|
% Closes the current output stream.
|
|
% The current output stream reverts to standard output.
|
|
% This will throw an io.error exception if an I/O error occurs.
|
|
%
|
|
:- pred told(io::di, io::uo) is det.
|
|
|
|
% Closes the current binary output stream. The default binary output
|
|
% stream reverts to standard output. As per Prolog told/0. This will
|
|
% throw an io.error exception if an I/O error occurs.
|
|
%
|
|
:- pred told_binary(io::di, io::uo) is det.
|
|
|
|
%---------------------------------------------------------------------------%
|
|
%---------------------------------------------------------------------------%
|
|
|
|
:- implementation.
|
|
|
|
:- import_module deconstruct.
|
|
:- import_module int.
|
|
:- import_module require.
|
|
|
|
%---------------------------------------------------------------------------%
|
|
|
|
'=:='(X, X).
|
|
|
|
'=\\='(X, Y) :-
|
|
X \= Y.
|
|
|
|
'=='(X, X).
|
|
'\\=='(X, Y) :-
|
|
X \= Y.
|
|
|
|
'=..'(Term, Functor - Args) :-
|
|
deconstruct(Term, canonicalize, Functor, _Arity, Args).
|
|
|
|
% We use module qualifiers here to avoid overriding
|
|
% the builtin Prolog versions.
|
|
prolog.arg(ArgumentIndex, Type, Univ) :-
|
|
deconstruct.arg(Type, canonicalize, ArgumentIndex - 1, Arg),
|
|
type_to_univ(Arg, Univ).
|
|
|
|
det_arg(ArgumentIndex, Type, Argument) :-
|
|
( if arg(ArgumentIndex, Type, Arg) then
|
|
Argument = Arg
|
|
else
|
|
error("det_arg: arg failed")
|
|
).
|
|
|
|
%---------------------------------------------------------------------------%
|
|
%
|
|
% Prolog-style predicates for opening and switching streams.
|
|
%
|
|
|
|
see(File, Result, !IO) :-
|
|
io.open_input(File, Result0, !IO),
|
|
(
|
|
Result0 = ok(Stream),
|
|
io.set_input_stream(Stream, _, !IO),
|
|
Result = ok
|
|
;
|
|
Result0 = error(Error),
|
|
Result = error(Error)
|
|
).
|
|
|
|
see_binary(File, Result, !IO) :-
|
|
io.open_binary_input(File, Result0, !IO),
|
|
(
|
|
Result0 = ok(Stream),
|
|
io.set_binary_input_stream(Stream, _, !IO),
|
|
Result = ok
|
|
;
|
|
Result0 = error(Error),
|
|
Result = error(Error)
|
|
).
|
|
|
|
%---------------------%
|
|
|
|
seen(!IO) :-
|
|
io.stdin_stream(Stdin, !IO),
|
|
io.set_input_stream(Stdin, OldStream, !IO),
|
|
io.close_input(OldStream, !IO).
|
|
|
|
seen_binary(!IO) :-
|
|
io.stdin_binary_stream(Stdin, !IO),
|
|
io.set_binary_input_stream(Stdin, OldStream, !IO),
|
|
io.close_binary_input(OldStream, !IO).
|
|
|
|
%---------------------%
|
|
|
|
tell(File, Result, !IO) :-
|
|
io.open_output(File, Result0, !IO),
|
|
(
|
|
Result0 = ok(Stream),
|
|
io.set_output_stream(Stream, _, !IO),
|
|
Result = ok
|
|
;
|
|
Result0 = error(Msg),
|
|
Result = error(Msg)
|
|
).
|
|
|
|
tell_binary(File, Result, !IO) :-
|
|
io.open_binary_output(File, Result0, !IO),
|
|
(
|
|
Result0 = ok(Stream),
|
|
io.set_binary_output_stream(Stream, _, !IO),
|
|
Result = ok
|
|
;
|
|
Result0 = error(Msg),
|
|
Result = error(Msg)
|
|
).
|
|
|
|
%---------------------%
|
|
|
|
told(!IO) :-
|
|
io.stdout_stream(Stdout, !IO),
|
|
io.set_output_stream(Stdout, OldStream, !IO),
|
|
io.close_output(OldStream, !IO).
|
|
|
|
told_binary(!IO) :-
|
|
io.stdout_binary_stream(Stdout, !IO),
|
|
io.set_binary_output_stream(Stdout, OldStream, !IO),
|
|
io.close_binary_output(OldStream, !IO).
|
|
|
|
%---------------------------------------------------------------------------%
|
|
:- end_module prolog.
|
|
%---------------------------------------------------------------------------%
|