001: /**************************************************************************/
002: /* B O S S A */
003: /* A simple imperative object-oriented research language */
004: /* (c) Daniel Bonniot 1999 */
005: /* */
006: /* This program is free software; you can redistribute it and/or modify */
007: /* it under the terms of the GNU General Public License as published by */
008: /* the Free Software Foundation; either version 2 of the License, or */
009: /* (at your option) any later version. */
010: /* */
011: /**************************************************************************/package mlsub.typing.lowlevel;
012:
013: import java.util.*;
014:
015: /**
016: * List with mark/backtrack facility
017: *
018: * @author bonniot
019: */
020:
021: public class BackableList {
022: public BackableList() {
023: content = new ArrayList();
024: }
025:
026: public BackableList(int capacity) {
027: content = new ArrayList(capacity);
028: }
029:
030: /****************************************************************
031: * Markup/Backtrack
032: ****************************************************************/
033:
034: public void mark() {
035: backups.push(content);
036: content = (ArrayList) content.clone();
037: }
038:
039: public void backtrack() {
040: content = (ArrayList) backups.pop();
041: }
042:
043: /****************************************************************
044: * List implementation
045: ****************************************************************/
046:
047: public void add(Object element) {
048: if (iterationInProgress)
049: waitingElements.push(element);
050: else
051: content.add(element);
052: }
053:
054: public void remove(Object element) {
055: if (iterationInProgress)
056: throw new InternalError(
057: "remove during iteration in BackableList");
058:
059: content.remove(element);
060: }
061:
062: public boolean contains(Object element) {
063: return content.contains(element);
064: }
065:
066: public void clear() {
067: content.clear();
068: }
069:
070: public Iterator iterator() {
071: if (iterationInProgress)
072: throw new InternalError(
073: "Concurrent iterations in BackableList");
074:
075: iterationInProgress = true;
076: return content.iterator();
077: }
078:
079: public void endOfIteration() {
080: if (!iterationInProgress)
081: throw new InternalError(
082: "No iterations to end in BackableList");
083:
084: iterationInProgress = false;
085: while (!waitingElements.empty())
086: content.add(waitingElements.pop());
087: }
088:
089: public String toString() {
090: return content.toString();
091: }
092:
093: private ArrayList content;
094: private Stack backups = new Stack();
095:
096: // We want to allow the addition of elements
097: // while iterating on the list.
098: // It is done by postponing the addition
099: // until the iteration is declared explicitely to be done
100: // ( with endOfIteration() ).
101: private boolean iterationInProgress = false;
102: private Stack waitingElements = new Stack();
103: }
|