The easiest way of doing input/output in Prolog is using the so-called DEC-10 predicates. They are based on the idea of having a current input and output, which can be redirected to write to and read from files. The basic DEC-10 I/O predicates are shown in Table 4.4.
There are more sophisticated I/O predicates based on opening and closing streams explicitly: handles to the files are returned, which can be passed to the I/O predicates. The interface is similar to what is provided by most operating systems, and available in many programming languages.
All I/O predicates perform side-effects: they change the state of the world (changing the contents of the screen or a disk file, in this case; broadcasting messages over the net, if writing / reading is made on a socket stream) in such a way that persists even after backtracking. Side-effects predicates are not easily formalized from a logical point of view, because the state of the whole world has to be taken into account.