Picat Functions vs. Predicates 4 — Questions and Answers
Question 1: What does Picat's `to_string/1` function do that a predicate could not directly accomplish?
- It binds a variable through unification
- It returns a string value usable inline in expressions like `print(to_string(42) ++ "!")` (Correct answer)
- It asserts facts into the database
- It reads input from stdin
Correct answer: It returns a string value usable inline in expressions like `print(to_string(42) ++ "!")`
As a function, `to_string/1` returns a value immediately composable with operators like `++`.
Question 2: In Picat, which of the following correctly adds a guard to a predicate clause?
- classify(X) => positive, X > 0 => println(positive)
- classify(X), X > 0 => println(positive) (Correct answer)
- classify(X) :- X > 0 | println(positive)
- classify(X) => if X > 0 then println(positive) end
Correct answer: classify(X), X > 0 => println(positive)
In Picat, a guard is placed between the head and the `=>` neck using a comma: `Head, Guard => Body`.
Question 3: Picat functions can be higher-order. Which call correctly applies function `F` to value `X` and uses the result?
- call(F, X, Result)
- Result = apply(F, X)
- Result = F.apply(X)
- Result = call(F, X) (Correct answer)
Correct answer: Result = call(F, X)
In Picat, `call(F, X)` invokes a function reference `F` with argument `X` and returns the result.
Question 4: What is the key reason you cannot use a predicate directly inside a list comprehension expression in Picat?
- Predicates are not imported automatically
- List comprehensions expect expressions that yield values, which only functions provide (Correct answer)
- Predicates cannot accept list arguments
- List comprehensions only work with integers
Correct answer: List comprehensions expect expressions that yield values, which only functions provide
List comprehension expressions like `[f(X) : X in L]` require `f` to return a value, so `f` must be a function.
Question 5: A Picat module exports both `area/1` (function) and `print_area/1` (predicate). Which import style correctly handles both?
- import geometry [area/1, print_area/1]
- use_module(geometry)
- import geometry (Correct answer)
- Both A and C are valid
Correct answer: import geometry
`import ModuleName` imports all exported functions and predicates from the module.
Question 6: Consider `abs(X) = X, X >= 0 => X` and `abs(X) = -X`. What design pattern does this demonstrate?
- Mutual recursion
- Guarded function clauses with a fallback (Correct answer)
- Nondeterministic backtracking
- Tail-call optimization
Correct answer: Guarded function clauses with a fallback
The first clause has a guard `X >= 0`; if it fails, the second clause serves as the fallback.
Question 7: Which statement best describes how Picat handles a predicate that is called but immediately fails?
- An exception is raised automatically
- Control backtracks to the most recent choice point or the call fails (Correct answer)
- The predicate retries indefinitely
- The runtime returns `false` as a value
Correct answer: Control backtracks to the most recent choice point or the call fails
A failing predicate causes backtracking; if no choice point exists, the enclosing goal fails.
What does Picat's `to_string/1` function do that a predicate could not directly accomplish?