?Vars &:: +Domain- All elements of Vars have a value in the domain Domain
?X &< ?Y- X is before Y in the domain order
&<(?X, ?Y, ?Bool)- Reified version of X &< Y
?X &= ?Y- X is the same domain value as Y
&=(?X, ?Y, ?Bool)- Reified version of X &= Y
?X &=< ?Y- X is before or equal to Y in the domain order
&=<(?X, ?Y, ?Bool)- Reified version of X &=< Y
?X &> ?Y- X is after Y in the domain order
&>(?X, ?Y, ?Bool)- Reified version of X &> Y
?X &>= ?Y- X is after or equal to Y in the domain order
&>=(?X, ?Y, ?Bool)- Reified version of X &>= Y
?X &\= ?Y- X is different from Y in the domain
&\=(?X, ?Y, ?Bool)- Reified version of X &\= Y
alldifferent(?List)- All elements of List are different
alldifferent(?List, ?Cap)- No domain value occurs more than Cap times in List
atmost(++N, +List, ++Value)- Value occurs N times in List
element(?Index, ++List, ?Value)- Value is the Index'th element of List
get_domain_as_list(?, ?)- No description available
indomain(?X)- Nondeterministically instantiate to domain values
is_exact_solver_var(?)- No description available
is_solver_var(?)- No description available
msg(?X, ?Y, -MSG)- MSG is the most specific generalisation of X and Y representable with ic-symbolic domain variables
occurrences(+Value, +List, ?N)- Value occurs N times in List
rotate(?X, ?C, ?Y)- Y is C places after X in the (cyclic) domain order
rotate(?X, ?C, ?Y, ?Bool)- Reified version of rotate(X,C,Y)
shift(?X, ?C, ?Y)- Y is C places after X in the domain order
shift(?X, ?C, ?Y, ?Bool)- Reified version of shift(X,C,Y)
symbol_domain_index(?X, -Domain, -Index)- Map a symbolic domain variable/value to integer variable/value
symbols_domain_indices(+Xs, ?Domain, -Is)- Map symbolic domain variables/values to integer variables/values

export op(700, xfx, &::)export op(700, xfx, &=)export op(700, xfx, &\=)export op(700, xfx, &<)export op(700, xfx, &=<)export op(700, xfx, &>)export op(700, xfx, &>=)

This library is an add-on to library(ic) and implements variables over ordered symbolic domains, and constraints over such variables. This is in contrast to the basic library(ic), which implements only variables over numeric domains.

?- local domain(weekday(mo,tu,we,th,fr,sa,su)).declares a domain with name 'weekday' and values 'mo', 'tu' etc. The domain values are implicitly ordered, with 'mo' corresponding to 1, until 'su' corresponding to 7. Domain values must be unique within one ECLiPSe module, i.e. a symbolic value can belong to at most one domain.

?- X &:: weekday. X = X{[mo, tu, we, th, fr, sa, su]} Yes (0.00s cpu)or multiple variables using &:: /2.

- X &= Y
- X is the same as Y
- X &\= Y
- X is different from Y
- X &< Y
- X is strictly before Y in the domain order
- X &> Y
- X is strictly after Y in the domain order
- X &=< Y
- X is the same as Y, or before Y in the domain order
- X &>= Y
- X is the same as Y, or after Y in the domain order
- shift(X,C,Y)
- Y is C places after X in the domain order
- rotate(X,C,Y)
- like shift/3 but wraps at domain boundary
- element(Index,List,Value)
- Value occurs List at position Index

?- [X, Y] &:: weekday, X &< Y. X = X{[mo, tu, we, th, fr, sa]} Y = Y{[tu, we, th, fr, sa, su]} Yes (0.00s cpu) ?- X &:: weekday, X &=< we. X = X{[mo, tu, we]} Yes (0.00s cpu)

- alldifferent(List)
- All list elements are different
- occurrences(Value,List,N)
- Value occurs N times in List
- atmost(N,List,Value)
- Value occurs at most N times in List

Internally, symbolic domains are mapped to integer ranges from 1 up to the number of domain elements. The first value in the domain declaration corresponds to 1, the second to 2 and so on. Similarly, symbolic domain variables can be mapped to a corresponding IC integer variable. This mapping is accessible through the predicate symbol_domain_index/3:

?- symbol_domain_index(fr, D, I). D = weekday I = 5 Yes (0.00s cpu) ?- X &:: weekday, symbol_domain_index(X, D, I). X = X{[mo, tu, we, th, fr, sa, su]} D = weekday I = I{1 .. 7} Yes (0.00s cpu) ?- X &:: weekday, X &\= we, symbol_domain_index(X, D, I). X = X{[mo, tu, th, fr, sa, su]} D = weekday I = I{[1, 2, 4 .. 7]} Yes (0.00s cpu)The integer variable I mirrors the domain of the symbolic variable X and vice versa.

Because of the mapping of symbols to integers, new constraints over symbolic variables can be implemented simply by placing numeric (IC) constraints on the corresponding integer variables.

Similarly, the facilities of the ic_search library can be exploited when working with symbolic variables. Instead of labeling the symbolic variables, one can use the various facilities of ic_search to label the corresponding integer variables instead.

For efficiency reasons, the 'constrained' suspension list of the symbolic variable does not automatically get woken every time the domain changes (although it does get woken when the domain is initially attached, and when the variable gets instantiated). There are two solutions: (1) instead of suspending goals on the constrained-list of the symbolic variable, suspend them on the constrained-list of the corresponding integer variable. (2) Use a forwarding demon that suspends on the constrained-list of the integer variable and wakes the constrained-list of the symbolic variable:

symbol_domain_index(X, Domain, X_ic), suspend(notify_constrained(X), 2, X_ic->constrained)

**Author:**Joachim Schimpf**Copyright ©**Cisco Systems, Inc.**Date:**$Date: 2017/08/01 13:34:56 $

Generated from ic_symbolic.eci on 2017-09-08 15:30