Did you know ... | Search Documentation: |
![]() | The class PlFail (version 2) |
The PlFail
class is used for short-circuiting a function
when failure or an exception occurs and any errors will be handled in
the code generated by the PREDICATE() macro. See also
section 2.19.2).
For example, this code:
PREDICATE(unify_zero, 1) { if ( !PL_unify_integer(A1.C_, 0) ) return false; return true; }
can instead be written this way:
void PREDICATE(unify_zero, 1) { if ( !PL_unify_integer(A1.C_, 0) ) throw PlFail(); return true; }
or:
PREDICATE(unify_zero, 1) { PlCheck_PL(PL_unify_integer(t.C_, 0)); return true; }
or:
PREDICATE(unify_zero, 1) { PlCheckFail(A1.unify_integer(0)); return true; }
or:
PREDICATE(unify_zero, 1) { return A1.unify_integer(0); }
Using throw PlFail()
in performance-critical code can
cause a signficant slowdown. A simple benchmark showed a 15x to 20x
slowdown using throw PlFail()
compared to return
false
(comparing the first code sample above with the second and
third samples; the speed difference seems to have been because in the
second sample, the compiler did a better job of inlining). However, for
most code, this difference will be barely noticeable.
There was no significant performance difference between the C++ version and this C version:
static foreign_t unify_zero(term_t a1) { return PL_unify_integer(a1, 0); }
If one of the C "PL_" functions in SWI-Prolog.h
returns
failure, this can be either a Prolog-style failure (e.g. from
PL_unify() or PL_next_solution()) or an error. If the
failure is due to an error, it's usually best to immediately return to
Prolog - and this can be done with the PlCheckEx() function,
which turns a Prolog error into a C++ PlException
. PlCheck()
calls PlCheckEx() and additionally throws PlFail() if the failure is for
Prolog failure.
The code for PlCheck() is just
void PlCheck(int rc) { if ( !PlCheckEx(rc) ) throw PlFail(); }
PlCheckEx() calls PL_exception() to see if there is a
Prolog exception; if so, the Prolog exception is converted to a
PlException
object, which is then thrown. For more details
on the C++ exceptions, see section 2.17.