KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > eclipse > core > runtime > jobs > MultiRule


1 /*******************************************************************************
2  * Copyright (c) 2003, 2006 IBM Corporation and others.
3  * All rights reserved. This program and the accompanying materials
4  * are made available under the terms of the Eclipse Public License v1.0
5  * which accompanies this distribution, and is available at
6  * http://www.eclipse.org/legal/epl-v10.html
7  *
8  * Contributors:
9  * IBM - Initial API and implementation
10  *******************************************************************************/

11 package org.eclipse.core.runtime.jobs;
12
13 import java.util.ArrayList JavaDoc;
14
15 /**
16  * A MultiRule is a compound scheduling rule that represents a fixed group of child
17  * scheduling rules. A MultiRule conflicts with another rule if any of its children conflict
18  * with that rule. More formally, a compound rule represents a logical intersection
19  * of its child rules with respect to the <code>isConflicting</code> equivalence
20  * relation.
21  * <p>
22  * A MultiRule will never contain other MultiRules as children. If a MultiRule is provided
23  * as a child, its children will be added instead.
24  * </p>
25  * <p>
26  * This class is not intended to be subclassed by clients.
27  * </p>
28  * @since 3.0
29  */

30 public class MultiRule implements ISchedulingRule {
31     private ISchedulingRule[] rules;
32
33     /**
34      * Returns a scheduling rule that encompasses all provided rules. The resulting
35      * rule may or may not be an instance of <code>MultiRule</code>. If all
36      * provided rules are <code>null</code> then the result will be
37      * <code>null</code>.
38      *
39      * @param ruleArray An array of scheduling rules, some of which may be <code>null</code>
40      * @return a combined scheduling rule, or <code>null</code>
41      * @since 3.1
42      */

43     public static ISchedulingRule combine(ISchedulingRule[] ruleArray) {
44         ISchedulingRule result = null;
45         for (int i = 0; i < ruleArray.length; i++) {
46             if (ruleArray[i] == null)
47                 continue;
48             if (result == null) {
49                 result = ruleArray[i];
50                 continue;
51             }
52             result = combine(result, ruleArray[i]);
53         }
54         return result;
55     }
56
57     /**
58      * Returns a scheduling rule that encompasses both provided rules. The resulting
59      * rule may or may not be an instance of <code>MultiRule</code>. If both
60      * provided rules are <code>null</code> then the result will be
61      * <code>null</code>.
62      *
63      * @param rule1 a scheduling rule, or <code>null</code>
64      * @param rule2 another scheduling rule, or <code>null</code>
65      * @return a combined scheduling rule, or <code>null</code>
66      */

67     public static ISchedulingRule combine(ISchedulingRule rule1, ISchedulingRule rule2) {
68         if (rule1 == rule2)
69             return rule1;
70         if (rule1 == null)
71             return rule2;
72         if (rule2 == null)
73             return rule1;
74         if (rule1.contains(rule2))
75             return rule1;
76         if (rule2.contains(rule1))
77             return rule2;
78         MultiRule result = new MultiRule();
79         result.rules = new ISchedulingRule[] {rule1, rule2};
80         //make sure we don't end up with nested multi-rules
81
if (rule1 instanceof MultiRule || rule2 instanceof MultiRule)
82             result.rules = flatten(result.rules);
83         return result;
84     }
85
86     /*
87      * Collapses an array of rules that may contain MultiRules into an
88      * array in which no rules are MultiRules.
89      */

90     private static ISchedulingRule[] flatten(ISchedulingRule[] nestedRules) {
91         ArrayList JavaDoc myRules = new ArrayList JavaDoc(nestedRules.length);
92         for (int i = 0; i < nestedRules.length; i++) {
93             if (nestedRules[i] instanceof MultiRule) {
94                 ISchedulingRule[] children = ((MultiRule) nestedRules[i]).getChildren();
95                 for (int j = 0; j < children.length; j++)
96                     myRules.add(children[j]);
97             } else {
98                 myRules.add(nestedRules[i]);
99             }
100         }
101         return (ISchedulingRule[]) myRules.toArray(new ISchedulingRule[myRules.size()]);
102     }
103
104     /**
105      * Creates a new scheduling rule that composes a set of nested rules.
106      *
107      * @param nestedRules the nested rules for this compound rule.
108      */

109     public MultiRule(ISchedulingRule[] nestedRules) {
110         this.rules = flatten(nestedRules);
111     }
112
113     /**
114      * Creates a new scheduling rule with no nested rules. For
115      * internal use only.
116      */

117     private MultiRule() {
118         //to be invoked only by factory methods
119
}
120
121     /**
122      * Returns the child rules within this rule.
123      * @return the child rules
124      */

125     public ISchedulingRule[] getChildren() {
126         return (ISchedulingRule[]) rules.clone();
127     }
128
129     /* (non-Javadoc)
130      * @see org.eclipse.core.runtime.jobs.ISchedulingRule#contains(org.eclipse.core.runtime.jobs.ISchedulingRule)
131      */

132     public boolean contains(ISchedulingRule rule) {
133         if (this == rule)
134             return true;
135         if (rule instanceof MultiRule) {
136             ISchedulingRule[] otherRules = ((MultiRule) rule).getChildren();
137             //for each child of the target, there must be some child in this rule that contains it.
138
for (int other = 0; other < otherRules.length; other++) {
139                 boolean found = false;
140                 for (int mine = 0; !found && mine < rules.length; mine++)
141                     found = rules[mine].contains(otherRules[other]);
142                 if (!found)
143                     return false;
144             }
145             return true;
146         }
147         for (int i = 0; i < rules.length; i++)
148             if (rules[i].contains(rule))
149                 return true;
150         return false;
151     }
152
153     /* (non-Javadoc)
154      * @see org.eclipse.core.runtime.jobs.ISchedulingRule#isConflicting(org.eclipse.core.runtime.jobs.ISchedulingRule)
155      */

156     public boolean isConflicting(ISchedulingRule rule) {
157         if (this == rule)
158             return true;
159         if (rule instanceof MultiRule) {
160             ISchedulingRule[] otherRules = ((MultiRule) rule).getChildren();
161             for (int j = 0; j < otherRules.length; j++)
162                 for (int i = 0; i < rules.length; i++)
163                     if (rules[i].isConflicting(otherRules[j]))
164                         return true;
165         } else {
166             for (int i = 0; i < rules.length; i++)
167                 if (rules[i].isConflicting(rule))
168                     return true;
169         }
170         return false;
171     }
172
173     /*
174      * For debugging purposes only.
175      */

176     public String JavaDoc toString() {
177         StringBuffer JavaDoc buffer = new StringBuffer JavaDoc();
178         buffer.append("MultiRule["); //$NON-NLS-1$
179
int last = rules.length - 1;
180         for (int i = 0; i < rules.length; i++) {
181             buffer.append(rules[i]);
182             if (i != last)
183                 buffer.append(',');
184         }
185         buffer.append(']');
186         return buffer.toString();
187     }
188 }
189
Popular Tags