package Sequenic.T2 ; import java.util.* ; import java.util.logging.Logger; import Examples.Triangle; import Sequenic.T3.SuiteUtils.Inference.Comment; /** * Represents object pools. An instance of this class is called an * object pool, or simply pool. It is used by T2's test engine to keep * track of objects created and accessed during its executions --see * the explanation of the. * *

A Pool will be organized as follows. Essentially, it is a set * of objects. Let's call this set S. The pool contains an object * map, which is a mapping from unique integer keys to objects in * S. The pool also has a domain map, which is a mapping from * Class to 'domains'. If the domain map maps a Class C to a domain D, * then D is essentially a set of objects, all should be of class * C. Each domain will be implemented as a linked list of the integer * indices over the object map. */ public class XPool { private final static Comment comment = new Comment(Logger.getLogger(XPool.class.getName())) ; private HashMap objectMap ; private HashMap> domainMap ; private int objectCount ; /** * Just a random generator. */ //private Random rnd ; /** * Create an empty pool. */ public XPool() { objectMap = new HashMap() ; domainMap = new HashMap>() ; objectCount = 0 ; //rnd = new Random() ; } /** * Returns the number of objects in the pool. */ public int get_objectCount() { return objectCount ; } /** * This will reset the pool to whatever its normal starting * state. This method is called whenever a new execution is * started. The default behavior of this method is to empty the * pool. To create a pool that is pre-populated, make a subclass * and overide this method so that reset will fill the pool with * its pre-population. */ public void reset() { // originally HashMap, changed to LinkedHashMap to make iteration order // deterministic, to avoid tripping oracle generator objectMap = new LinkedHashMap() ; domainMap = new LinkedHashMap>() ; objectCount = 0 ; } /** * Returns the object from objectMap indexed with i. * *

Precond: i should be an existing index. */ public Object get(int i) { return objectMap.get(i) ; } /** * Draw an object of class C from the pool. It actually * returns the index of the object rather than the object * itself. It returns null if no instance of C is found in the * pool. * * WP: for the benchmark, this is changed to always return the first * index, to make it deterministic, rather than a random index. */ public Integer getIndex(Class C) { if (C == null) throw new IllegalArgumentException() ; // get all classes from the pool which are either C or // subclasses of C: LinkedList classes = new LinkedList() ; for (Class D : domainMap.keySet()) if (C.isAssignableFrom(D)) classes.add(D) ; if (classes.isEmpty()) { comment.with("No matching class is found!").end() ; return null ; } comment.with("Found a matching class").end(); // Now pick one domain randomly: //Class chosenClass = classes.get(rnd.nextInt(classes.size())) ; Class chosenClass = classes.getFirst() ; // now randomly pick an index from the corresponding domain: LinkedList domain = domainMap.get(chosenClass) ; // this branch is actually not feasible: // if (domain.isEmpty()) return null ; // else return domain.get(rnd.nextInt(domain.size())) ; // else int k = domain.getFirst() ; //System.err.print("### getIndex(" + C + ") -->" + k) ; return k ; } /** * Add an object u into the pool. It returns the index * of u in the pool's object map. */ public int put(Object u) { if (u==null || u==this) { comment.with("trying to put null, or the pool in itself").end() ; throw new IllegalArgumentException() ; } int index = objectCount ; Class C = u.getClass() ; objectCount++ ; objectMap.put(index,u) ; if (domainMap.containsKey(C)) (domainMap.get(C)) . add(index) ; else { comment.with("an object with an unseen class is added").end(); LinkedList domain = new LinkedList() ; domain.add(index) ; domainMap.put(C,domain) ; } return index ; } }