001: package org.drools.common;
002:
003: /*
004: * Copyright 2005 JBoss Inc
005: *
006: * Licensed under the Apache License, Version 2.0 (the "License");
007: * you may not use this file except in compliance with the License.
008: * You may obtain a copy of the License at
009: *
010: * http://www.apache.org/licenses/LICENSE-2.0
011: *
012: * Unless required by applicable law or agreed to in writing, software
013: * distributed under the License is distributed on an "AS IS" BASIS,
014: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
015: * See the License for the specific language governing permissions and
016: * limitations under the License.
017: */
018:
019: import org.drools.conflict.DepthConflictResolver;
020: import org.drools.spi.Activation;
021: import org.drools.spi.AgendaGroup;
022: import org.drools.spi.ConflictResolver;
023: import org.drools.util.BinaryHeapQueue;
024: import org.drools.util.Iterator;
025: import org.drools.util.LinkedList;
026: import org.drools.util.LinkedListEntry;
027: import org.drools.util.PrimitiveLongMap;
028: import org.drools.util.Queueable;
029: import org.drools.util.LinkedList.LinkedListIterator;
030:
031: /**
032: * <code>AgendaGroup</code> implementation that uses a <code>PriorityQueue</code> to prioritise the evaluation of added
033: * <code>ActivationQueue</code>s. The <code>AgendaGroup</code> also maintains a <code>Map</code> of <code>ActivationQueues</code>
034: * for requested salience values.
035: *
036: * @see PriorityQueue
037: * @see ActivationQueue
038: *
039: * @author <a href="mailto:mark.proctor@jboss.com">Mark Proctor</a>
040: * @author <a href="mailto:bob@werken.com">Bob McWhirter</a>
041: *
042: */
043: public class ArrayAgendaGroup implements InternalAgendaGroup {
044:
045: private static final long serialVersionUID = 400L;
046:
047: private final String name;
048:
049: /** Items in the agenda. */
050: private LinkedList[] array;
051:
052: private boolean active;
053:
054: private int size;
055:
056: private int index;
057:
058: private int lastIndex;
059:
060: /**
061: * Construct an <code>AgendaGroup</code> with the given name.
062: *
063: * @param name
064: * The <AgendaGroup> name.
065: */
066:
067: public ArrayAgendaGroup(final String name,
068: final InternalRuleBase ruleBase) {
069: this .name = name;
070: Integer integer = (Integer) ruleBase.getAgendaGroupRuleTotals()
071: .get(name);
072:
073: if (integer == null) {
074: this .array = new LinkedList[0];
075: } else {
076: this .array = new LinkedList[integer.intValue()];
077: }
078:
079: this .index = this .array.length - 1;
080: this .lastIndex = 0;
081: }
082:
083: /* (non-Javadoc)
084: * @see org.drools.spi.AgendaGroup#getName()
085: */
086: public String getName() {
087: return this .name;
088: }
089:
090: public void clear() {
091: this .array = new LinkedList[this .array.length];
092: }
093:
094: /* (non-Javadoc)
095: * @see org.drools.spi.AgendaGroup#size()
096: */
097: public int size() {
098: return this .size;
099: }
100:
101: public void add(final Activation activation) {
102: AgendaItem item = (AgendaItem) activation;
103: this .size++;
104: int seq = item.getSequenence();
105:
106: if (seq < this .index) {
107: this .index = seq;
108: }
109:
110: if (seq > this .lastIndex) {
111: this .lastIndex = seq;
112: }
113:
114: LinkedList list = this .array[seq];
115: if (list == null) {
116: list = new LinkedList();
117: this .array[item.getSequenence()] = list;
118: }
119:
120: list.add(new LinkedListEntry(activation));
121: }
122:
123: public Activation getNext() {
124: Activation activation = null;
125: while (this .index <= lastIndex) {
126: LinkedList list = this .array[this .index];
127: if (list != null) {
128: activation = (Activation) ((LinkedListEntry) list
129: .removeFirst()).getObject();
130: if (list.isEmpty()) {
131: this .array[this .index++] = null;
132: }
133: this .size--;
134: break;
135: }
136: this .index++;
137: }
138: return (Activation) activation;
139: }
140:
141: public boolean isActive() {
142: return this .active;
143: }
144:
145: public void setActive(final boolean activate) {
146: this .active = activate;
147: }
148:
149: /**
150: * Iterates a PriorityQueue removing empty entries until it finds a populated entry and return true,
151: * otherwise it returns false;
152: *
153: * @param priorityQueue
154: * @return
155: */
156: public boolean isEmpty() {
157: return this .size == 0;
158: }
159:
160: public Activation[] getActivations() {
161: Activation[] activations = new Activation[this .size];
162: int j = 0;
163: for (int i = 0; i < this .array.length; i++) {
164: ;
165: LinkedList list = this .array[i];
166: if (list != null) {
167: Iterator it = list.iterator();
168: Activation activation = (Activation) ((LinkedListEntry) it
169: .next()).getObject();
170: while (activation != null) {
171: activations[j++] = activation;
172: activation = (Activation) it.next();
173: }
174: }
175:
176: }
177: return activations;
178: }
179:
180: public Activation[] getQueue() {
181: return getActivations();
182: }
183:
184: public String toString() {
185: return "AgendaGroup '" + this .name + "'";
186: }
187:
188: public boolean equal(final Object object) {
189: if ((object == null) || !(object instanceof ArrayAgendaGroup)) {
190: return false;
191: }
192:
193: if (((ArrayAgendaGroup) object).name.equals(this .name)) {
194: return true;
195: }
196:
197: return false;
198: }
199:
200: public int hashCode() {
201: return this.name.hashCode();
202: }
203: }
|