Modules - fuzzy
When reasoning about natural systems, it is rarely the case that results are precisely true or precisely false. For example, we might agree that 3 degrees celcius is "cold", but what about 10 degrees celcius? Where is the cut-off point between "cold" and "not cold"? In reality, 10 degrees is still "somewhat cold".
As another example, a person who is 10 years old may be considered "young". But what about a person who is 30 years old? Compared to an 80 year old person, 30 is still "relatively young". Once again, the cut-off point is not exact.
Fuzzy logic allows us to express relationships like "somewhat cold" and "relatively young" by using a range of values between 0 and 1. We might assign the value 1 to the statement "3 degrees celcius is cold", 0.7 to the statement "10 degrees
celcius is cold", and 0.2 to the statement "30 years old is young".
Note: all of the predicates defined below require an explicit import of the fuzzy
module:
Statements and expressions in Plang have an associated fuzzy value that ranges between 0 and 1 and indicates the degree of confidence that the application has in the result. If a statement does not involve fuzzy operations, then its confidence value will be set to 1 if it succeeds or 0 if it fails. Most built-in predicates and statements in Plang fall into this category.
Confidence values for facts can be expressed directly on the clause for the fact:
cold(3) <<1.0>>.
cold(10) <<0.7>>.
cold(27) <<0.0>>.
This works well for discrete facts, but not as well for continuous values like temperature. A better way to define "cold" is to compute the fuzzy confidence value based on the incoming temperature:
cold(Temperature)
{
fuzzy(1.0 - (Temperature - 3.0) / 24.0);
}
The fuzzy/1 predicate evaluates its argument, clamps it to the range 0 to 1, and then alters the application's current_confidence value according to the following formula:
- new_confidence = min(current_confidence, confidence(Statement))
where confidence(Statement) is the fuzzy confidence value produced by executing Statement. Multiple executions of a fuzzy/1 statement will accumulate a final fuzzy confidence value that is the minimum of all intermediate values. For example, if the initial fuzzy confidence value is 1, then the following predicate will reduce it to 0.5 (the minimum of 1, 0.6, 0.5, and 0.8):
foo()
{
fuzzy(0.6);
fuzzy(0.5);
fuzzy(0.8);
}
If the current fuzzy confidence value reduces to zero, then a fail and backtrack will occur.
In the previous section, we used the default AND rule for combining confidence values. Confidence values can also be combined explicitly using the Zadeh operators for AND, OR, and NOT:
- confidence(fuzzy_and(A, B)) = min(confidence(A), confidence(B))
- confidence(fuzzy_or(A, B)) = max(confidence(A), confidence(B))
- confidence(fuzzy_not(A)) = 1 - confidence(A)
The fuzzy_and/2 operator is a convenience predicate: fuzzy_and(A, B) is equivalent to the statement sequence A ; B. That is, the following two statement sequences are equivalent:
cold(Temperature);
low_pressure(Pressure);
fuzzy_and(cold(Temperature), low_pressure(Pressure));
Plang also provides two "product" operators that can be used as alternatives for AND and OR ("product NOT" is the same as Zadeh NOT):
- confidence(fuzzy_prod(A, B)) = confidence(A) * confidence(B)
- confidence(fuzzy_prod_or(A, B)) = confidence(A) + confidence(B) - confidence(A) * confidence(B)
Both the Zadeh operators and the product operators obey De Morgan's laws:
- confidence(fuzzy_not(fuzzy_and(A, B))) = confidence(fuzzy_or(fuzzy_not(A), fuzzy_not(B)))
- confidence(fuzzy_not(fuzzy_or(A, B))) = confidence(fuzzy_and(fuzzy_not(A), fuzzy_not(B)))
- confidence(fuzzy_not(fuzzy_prod(A, B))) = confidence(fuzzy_prod_or(fuzzy_not(A), fuzzy_not(B)))
- confidence(fuzzy_not(fuzzy_prod_or(A, B))) = confidence(fuzzy_prod(fuzzy_not(A), fuzzy_not(B)))
Definite clause grammar rules can be annotated to express the degree of confidence that the rule has in a particular sentence parse:
verb_phrase --> verb <<0.7>>.
verb_phrase --> verb, noun_phrase <<0.3>>.
When a grammar is ambiguous, this can help determine which of several parses for a sentence is the most likely.
(<<...>>)/1, fuzzy/1, fuzzy/2, fuzzy_and/2, fuzzy_findall/3, fuzzy_findall_sorted/3, fuzzy_not/1, fuzzy_or/2, fuzzy_prod/2, fuzzy_prod_or/2, set_fuzzy/1
fuzzy/1,
(<<...>>)/1 - adjusts the current fuzzy confidence value.
- Usage
- fuzzy(Expr)
- head(...) << Expr >> { Body }
- Description
- If Expr is a variable, then unifies Expr with the current fuzzy confidence value.
- If Expr is not a variable, then the rules of is/2 are used to evaluate Expr to a number. If Expr is less than or equal to zero, then fail. Otherwise set the current fuzzy confidence value to the minimum of Expr and the current fuzzy confidence value.
- The current fuzzy confidence value can only be adjusted downwards by this predicate. The current fuzzy confidence value is initialized by the system to 1, so values of Expr greater than 1 will be ignored.
- The (<<...>>)/1 form can only be used in the head of a clause, just before the Body, and Expr must be a constant floating-point or integer value.
- Errors
type_error(number, Expr)
- Expr is not a variable and it did not evaluate to a number.
- Examples
cold(3) <<1.0>>.
cold(10) <<0.7>>.
cold(27) <<0.0>>.
cold(Temperature)
{
fuzzy(1.0 - (Temperature - 3.0) / 24.0);
}
- See Also
- fuzzy/2, is/2, set_fuzzy/1
fuzzy/2 - adjusts the current fuzzy confidence value according to an interval list.
- Usage
- fuzzy(Expr, List)
- Description
- Evaluates Expr according to the rules of is/2.
- List must have the form [(Value1, Fuzzy1), (Value2, Fuzzy2), ..., (ValueN, FuzzyN)], where the Valuei members are in ascending order. The predicate searches List for Expr to determine a fuzzy adjustment value.
- If Expr is less than Value1, then the fuzzy adjustment value is set to Fuzzy1. If Expr is greater than ValueN, then the fuzzy adjustment value is set to FuzzyN. Otherwise a linear interpolation between Fuzzyi and Fuzzyi+1 is performed to determine the fuzzy adjustment value, where Expr falls between Valuei and Valuei+1.
- If the fuzzy adjustment value is less than or equal to zero, then fail. Otherwise set the current fuzzy confidence value to the minimum of the fuzzy adjustment value and the current fuzzy confidence value.
- Errors
type_error(number, Expr)
- Expr did not evaluate to a number.
instantiation_error
- List is a variable.
type_error(interval_list, List)
- List is not a valid interval list.
- Examples
cold(Temperature)
{
fuzzy(Temperature, [(1, 3), (27, 0)]);
}
- See Also
- fuzzy/1, is/2
fuzzy_and/2 - Zadeh AND operator for fuzzy logic.
- Usage
- fuzzy_and(Goal1, Goal2)
- Description
- Executes Goal1 and then Goal2. The new fuzzy confidence value is computed from the confidence values for Goal1 and Goal2 as follows:
- new_confidence = min(current_confidence, min(confidence(Goal1), confidence(Goal2)))
- The fuzzy_and/2 predicate is equivalent to executing the statement sequence Goal1 ; Goal2.
- Examples
fuzzy_and(cold(Temperature), low_pressure(Pressure));
cold(Temperature); low_pressure(Pressure);
- See Also
- (&&)/2, fuzzy/1, fuzzy_not/1, fuzzy_or/2, fuzzy_prod/2
fuzzy_findall/3 - find all solutions to a goal and their fuzzy confidence values.
- Usage
- fuzzy_findall(Term, Goal, List)
- Description
- Executes Goal multiple times until it fails. Every time it succeeds, record (Term, Confidence) in List where Confidence is the fuzzy confidence value corresponding to that solution.
- Errors
instantiation_error
- Goal is a variable.
type_error(callable, Goal)
- Goal or some part of Goal is not callable.
type_error(list, List)
- List is not a variable, list, or partial list.
- Examples
cold(3) <<1.0>>.
cold(10) <<0.7>>.
cold(27) <<0.0>>.
fuzzy_findall(T, cold(T), List);
results in: List = [(3, 1.0), (10, 0.7)]
- See Also
- findall/3, fuzzy/1, fuzzy_findall_sorted/3
fuzzy_findall_sorted/3 - find all solutions to a goal and sort them on their fuzzy confidence values.
- Usage
- fuzzy_findall_sorted(Term, Goal, List)
- Description
- Executes Goal multiple times until it fails. Every time it succeeds, record (Term, Confidence) in List where Confidence is the fuzzy confidence value corresponding to that solution.
- The returned List will be ordered from the highest fuzzy confidence value to the lowest. If two or more elements have the same fuzzy confidence value, then the ordering of the equal solutions is the same as for fuzzy_findall/3.
- Errors
instantiation_error
- Goal is a variable.
type_error(callable, Goal)
- Goal or some part of Goal is not callable.
type_error(list, List)
- List is not a variable, list, or partial list.
- Examples
warm(3) <<0.0>>.
warm(10) <<0.3>>.
warm(27) <<1.0>>.
fuzzy_findall_sorted(T, warm(T), List);
results in: List = [(27, 1.0), (10, 0.3)]
- See Also
- findall/3, fuzzy/1, fuzzy_findall/3
fuzzy_not/1 - NOT operator for fuzzy logic.
- Usage
- fuzzy_not(Goal)
- Description
- Executes Goal. The new fuzzy confidence value is computed from the confidence value for Goal as follows:
- new_confidence = min(current_confidence, 1 - confidence(Goal1))
- If Goal fails, then confidence(Goal) is taken to be 0. If Goal succeeds but did not involve fuzzy terms, then confidence(Goal) is taken to be 1 (and then fuzzy_not(Goal) fails).
- Examples
- See Also
- (!)/1, fuzzy/1, fuzzy_and/2, fuzzy_or/2, fuzzy_prod/2, fuzzy_prod_or/2
fuzzy_or/2 - Zadeh OR operator for fuzzy logic.
- Usage
- fuzzy_or(Goal1, Goal2)
- Description
- Executes Goal1 and then Goal2. The new fuzzy confidence value is computed from the confidence values for Goal1 and Goal2 as follows:
- new_confidence = min(current_confidence, max(confidence(Goal1), confidence(Goal2)))
- This predicate differs from (||)/2 in that it will evaluate Goal1 and Goal2 at the same time rather than treating them as alternative execution paths as (||)/2 does.
- Examples
fuzzy_or(cold(Temperature), low_pressure(Pressure))
- See Also
- (||)/2, fuzzy/1, fuzzy_and/2, fuzzy_not/1, fuzzy_prod_or/2
fuzzy_prod/2 - product AND operator for fuzzy logic.
- Usage
- fuzzy_prod(Goal1, Goal2)
- Description
- Executes Goal1 and then Goal2. The new fuzzy confidence value is computed from the confidence values for Goal1 and Goal2 as follows:
- new_confidence = min(current_confidence, confidence(Goal1) * confidence(Goal2))
- This operator is useful for reasoning about probabilities where the probability of two independent events occurring in combination is their product, not their minimum.
- The fuzzy_prod_or/2 and fuzzy_not/1 operators provide the logical OR and NOT counterparts to fuzzy_prod/2.
- Examples
fuzzy_prod(cold(Temperature), low_pressure(Pressure))
- See Also
- fuzzy/1, fuzzy_and/2, fuzzy_not/1, fuzzy_prod_or/2
fuzzy_prod_or/2 - product OR operator for fuzzy logic.
- Usage
- fuzzy_prod_or(Goal1, Goal2)
- Description
- Executes Goal1 and then Goal2. The new fuzzy confidence value is computed from the confidence values for Goal1 and Goal2 as follows:
- new_confidence = min(current_confidence, confidence(Goal1) + confidence(Goal2) - confidence(Goal1) * confidence(Goal2))
- The fuzzy_prod/2 and fuzzy_not/1 operators provide the logical AND and NOT counterparts to fuzzy_prod_or/2.
- Examples
fuzzy_prod_or(cold(Temperature), low_pressure(Pressure))
- See Also
- fuzzy/1, fuzzy_not/1, fuzzy_or/2, fuzzy_prod/2
set_fuzzy/1 - sets the current fuzzy confidence value.
- Usage
- set_fuzzy(Expr)
- Description
- Evaluates Expr according to the rules of is/2. If Expr is less than or equal to zero, then fail. If Expr is greater than 1, then set the current fuzzy confidence value to 1. Otherwise set the current fuzzy confidence value to Expr.
- Note: this predicate should be used sparingly as it breaks logical consistency. In most circumstances, the fuzzy/1 predicate should be used instead. The usual scenario for set_fuzzy/1 is to set the current fuzzy confidence value back to 1 to start a new fuzzy computation.
- Errors
type_error(number, Expr)
- Expr did not evaluate to a number.
- Examples
set_fuzzy(1)
set_fuzzy(0)
- See Also
- fuzzy/1