@eagleoutice/flowr-dev
Version:
Static Dataflow Analyzer and Program Slicer for the R Programming Language
97 lines • 3.46 kB
JavaScript
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.BoundedSetDomain = exports.SetBottom = void 0;
const set_1 = require("../../util/collections/set");
const logic_1 = require("../../util/logic");
const abstract_domain_1 = require("./abstract-domain");
const lattice_1 = require("./lattice");
/** The Bottom element of the bounded set domain as empty set */
exports.SetBottom = new Set();
/**
* The bounded set abstract domain as sets of possible values bounded by a `limit` indicating the maximum number of inferred values.
* The Bottom element is defined as the empty set and the Top element is defined as {@link Top} symbol.
* @template T - Type of the values in the abstract domain
* @template Value - Type of the constraint in the abstract domain (Top, Bottom, or an actual value)
*/
class BoundedSetDomain extends abstract_domain_1.AbstractDomain {
limit;
setType;
/**
* @param limit - A limit for the maximum number of elements to store in the set
* @param setType - An optional set constructor for the domain elements if the type `T` is not storable in a HashSet
*/
constructor(value, limit = abstract_domain_1.DEFAULT_INFERENCE_LIMIT, setType = Set) {
if (value !== lattice_1.Top) {
if (Array.isArray(value)) {
super((value.length > limit ? lattice_1.Top : new setType(value)));
}
else {
super((value.size > limit ? lattice_1.Top : new setType(value)));
}
}
else {
super(value);
}
this.limit = limit;
this.setType = setType;
}
create(value) {
return new BoundedSetDomain(value, this.limit, this.setType);
}
from(...values) {
return this.create(values);
}
static top(limit, setType) {
return new this(lattice_1.Top, limit, setType);
}
static bottom(limit, setType) {
return new this(exports.SetBottom, limit, setType);
}
static from(values, limit, setType) {
return new this(Array.isArray(values) ? values : [values], limit, setType);
}
top() {
return this.create(lattice_1.Top);
}
bottom() {
return this.create(exports.SetBottom);
}
equalsValue(other) {
return (0, set_1.setEquals)(this.value, other.value);
}
leqValue(other) {
return this.value.isSubsetOf(other.value);
}
joinValue(other) {
return this.create(this.value.union(other.value));
}
meetValue(other) {
return this.create(this.value.intersection(other.value));
}
satisfies(value) {
if (this.isValue() && this.value.has(value)) {
return this.value.size === 1 ? logic_1.Ternary.Always : logic_1.Ternary.Maybe;
}
else if (this.isTop()) {
return logic_1.Ternary.Maybe;
}
return logic_1.Ternary.Never;
}
jsonify() {
return this.value.values().toArray();
}
stringify() {
return `{${this.value.values().map(abstract_domain_1.AbstractDomain.toString).toArray().join(', ')}}`;
}
isTop() {
return this.value === lattice_1.Top;
}
isBottom() {
return this.value !== lattice_1.Top && this.value.size === 0;
}
isValue() {
return this.value !== lattice_1.Top;
}
}
exports.BoundedSetDomain = BoundedSetDomain;
//# sourceMappingURL=bounded-set-domain.js.map