Clover icon

Coverage Report

  1. Project Clover database Thu Aug 13 2020 12:04:21 BST
  2. Package com.stevesoft.pat

File Pattern.java

 

Coverage histogram

../../../img/srcFileCovDistChart8.png
20% of files have more coverage

Code metrics

48
78
18
1
298
192
43
0.55
4.33
18
2.39

Classes

Class Line # Actions
Pattern 23 78 43
0.715277871.5%
 

Contributing tests

This file is covered by 44 tests. .

Source view

1    //
2    // This software is now distributed according to
3    // the Lesser Gnu Public License. Please see
4    // http://www.gnu.org/copyleft/lesser.txt for
5    // the details.
6    // -- Happy Computing!
7    //
8    package com.stevesoft.pat;
9   
10    import jalview.util.MessageManager;
11   
12    import java.util.Hashtable;
13   
14    /**
15    Shareware: package pat
16    <a href="copyright.html">Copyright 2001, Steven R. Brandt</a>
17    */
18    /**
19    * Class Pattern is the base class on which all the other pattern elements are
20    * built.
21    */
22   
 
23    public abstract class Pattern
24    {
25    /**
26    * The ESC character, the user can provide his own value for the escape
27    * character through regex.esc
28    */
29    public final static char ESC = '\\';
30   
31    final static String PROTECT_THESE = "[]{}(),$,-\"^.";
32   
33    /**
34    * The interal match function, it must be provided by any class which wishes
35    * to extend Pattern.
36    */
37    public abstract int matchInternal(int i, Pthings p);
38   
39    public abstract String toString();
40   
41    // Class Pattern is a singly linked list
42    // chained together by member next. The member
43    // parent is used so that sub patterns can access
44    // the chain they are branching from.
45    Pattern next = null, parent = null;
46   
47    /**
48    * This gets the next element of a Pattern that we wish to match. If we are at
49    * the end of a subchain of patterns, it will return us to the parent chain.
50    */
 
51  359029 toggle public Pattern getNext()
52    {
53  276511 return next != null ? next : (parent == null ? null : parent.getNext());
54    }
55   
56    /**
57    * Call this method if you have a pattern element that takes a sub pattern
58    * (such as Or), and after you have added a sub pattern to the current pattern
59    * element.
60    */
 
61  15771 toggle public void setParent(Pattern p)
62    {
63  15771 if (next != null)
64    {
65  272 next.setParent(p);
66    }
67    else
68    {
69  15499 parent = p;
70    }
71    }
72   
73    /**
74    * This determines if the remainder of a Pattern matches. Type "return
75    * nextMatch" from within matchInternal if the current Pattern matches.
76    * Otherwise, return a -1.
77    */
 
78  339045 toggle public int nextMatch(int i, Pthings pt)
79    {
80  339045 Pattern p = getNext();
81    /*
82    * if(p == null) return i; return p.matchInternal(i,pt);
83    */
84  339045 return p == null ? i : p.matchInternal(i, pt);
85    }
86   
87    /**
88    * This is a toString() for the remainder of the Pattern elements after this
89    * one. use this when overriding toString(). Called from within toString().
90    */
 
91  0 toggle public String nextString()
92    {
93  0 if (next == null)
94    {
95  0 return "";
96    }
97  0 return next.toString();
98    }
99   
100    /** a method to detect whether char c is in String s */
 
101  0 toggle final static boolean inString(char c, String s)
102    {
103  0 int i;
104  0 for (i = 0; i < s.length(); i++)
105    {
106  0 if (s.charAt(i) == c)
107    {
108  0 return true;
109    }
110    }
111  0 return false;
112    }
113   
114    /**
115    * A method to create a string that protects the characters listed in
116    * PROTECT_THESE by prepending the esc character. The esc character itself is
117    * automatically protected.
118    */
 
119  0 toggle final static String protect(String s, String PROTECT_THESE, char esc)
120    {
121  0 int i;
122  0 StringBuffer sb = new StringBuffer();
123  0 String p = PROTECT_THESE + esc;
124  0 for (i = 0; i < s.length(); i++)
125    {
126  0 char c = s.charAt(i);
127  0 if (inString(c, p))
128    {
129  0 sb.append(esc);
130    }
131  0 sb.append(c);
132    }
133  0 return sb.toString();
134    }
135   
136    /**
137    * This can be used to perform a match test from within class Pattern.
138    */
 
139  0 toggle public int match(StringLike s, Pthings pt)
140    {
141  0 return matchAt(s, 0, pt);
142    }
143   
144    /**
145    * This can be used to perform a match test from within class Pattern.
146    */
 
147  380687 toggle public int matchAt(StringLike s, int i, Pthings pt)
148    {
149  380687 pt.src = s;
150  380687 int r = matchInternal(i, pt);
151  380687 if (r < 0)
152    {
153  374979 return -1;
154    }
155  5708 mfrom = r < i ? r + 1 : i;
156  5708 return r < i ? i - r - 1 : r - i;
157    }
158   
159    int mfrom = 0;
160   
161    // Detect masked characters
 
162  331907 toggle final boolean Masked(int i, Pthings pt)
163    {
164  331907 return pt.cbits == null ? false : pt.cbits.get(i);
165    }
166   
167    /** add a Pattern to the singly-linked Pattern chain. */
 
168  9455 toggle public Pattern add(Pattern p)
169    {
170  9455 if (next == null)
171    {
172  3578 if (p == null)
173    {
174  2 return this;
175    }
176  3576 next = p;
177  3576 p.parent = parent;
178  3576 parent = null;
179    }
180    else
181    {
182  5877 next.add(p);
183    }
184  9453 return this;
185    }
186   
187    /**
188    * The minimum number of characters which this pattern element can match.
189    */
 
190  422 toggle public patInt minChars()
191    {
192  422 return new patInt(0);
193    }
194   
195    /**
196    * The maximum number of characters which this pattern element can match.
197    */
 
198  0 toggle public patInt maxChars()
199    {
200  0 return new patInf();
201    }
202   
203    /** return minimum number of characters in pattern */
 
204  3990 toggle public final patInt countMinChars()
205    {
206  3990 Pattern p = this;
207  3990 patInt sum = new patInt(0);
208  8094 while (p != null)
209    {
210  4104 sum.pluseq(p.minChars());
211  4104 p = p.next;
212    }
213  3990 return sum;
214    }
215   
216    /** return maximum number of characters in pattern */
 
217  550 toggle public final patInt countMaxChars()
218    {
219  550 Pattern p = this;
220  550 patInt sum = new patInt(0);
221  1159 while (p != null)
222    {
223  609 sum.pluseq(p.maxChars());
224  609 p = p.next;
225    }
226  550 return sum;
227    }
228   
229    // This method is only needed by Multi_stage2 so far...
230    // the reason is that it may try something else after a
231    // match succeeds. OrMark will only record the last thing
232    // tried in marks, so we need to backup the result of the
233    // last successful match and restore it if the next one
234    // does not succeed.
 
235  358 toggle final int testMatch(Pattern p, int pos, Pthings pt)
236    {
237  358 int[] tab = null;
238  358 if (pt.marks != null)
239    {
240  350 try
241    {
242  350 tab = new int[pt.marks.length];
243  1750 for (int i = 0; i < tab.length; i++)
244    {
245  1400 tab[i] = pt.marks[i];
246    }
247    } catch (Throwable t)
248    {
249    }
250    }
251  358 int ret = p.matchInternal(pos, pt);
252  358 if (ret < 0)
253    {
254  8 pt.marks = tab;
255    }
256  358 return ret;
257    }
258   
259    /**
260    * Clones this pattern elements without cloning others in the linked list.
261    */
 
262  0 toggle Pattern clone1(Hashtable h)
263    {
264  0 throw new Error(MessageManager.formatMessage(
265    "error.no_such_method_as_clone1_for", new String[] { getClass()
266    .getName() }));
267    }
268   
 
269  9177 toggle Pattern clone(Hashtable h)
270    {
271  9177 Pattern p = (Pattern) h.get(this);
272  9177 if (p != null)
273    {
274  3542 return p;
275    }
276  5635 p = clone1(h);
277  5635 if (p == null)
278    {
279  0 throw new Error(MessageManager.getString("error.null_from_clone1"));
280    }
281  5635 h.put(this, p);
282  5635 h.put(p, p);
283  5635 if (next != null)
284    {
285  805 p.next = next.clone(h);
286    }
287  5635 if (parent != null)
288    {
289  3542 p.parent = parent.clone(h);
290    }
291  5635 return p;
292    }
293   
 
294  8050 toggle public boolean equals(Object o)
295    {
296  8050 return o == this;
297    }
298    };