📄 re.java
字号:
case OP_BRANCH:
{
// Check for choices
if (instruction[next + offsetOpcode] != OP_BRANCH)
{
// If there aren't any other choices, just evaluate this branch.
node += nodeSize;
continue;
}
// Try all available branches
short nextBranch;
do
{
// Try matching the branch against the string
if ((idxNew = matchNodes(node + nodeSize, maxNode, idx)) != -1)
{
return idxNew;
}
// Go to next branch (if any)
nextBranch = (short)instruction[node + offsetNext];
node += nextBranch;
}
while (nextBranch != 0 && (instruction[node + offsetOpcode] == OP_BRANCH));
// Failed to match any branch!
return -1;
}
case OP_NOTHING:
case OP_GOTO:
// Just advance to the next node without doing anything
break;
case OP_END:
// Match has succeeded!
setParenEnd(0, idx);
return idx;
default:
// Corrupt program
internalError("Invalid opcode '" + opcode + "'");
}
// Advance to the next node in the program
node = next;
}
// We "should" never end up here
internalError("Corrupt program");
return -1;
}
/**
* Match the current regular expression program against the current
* input string, starting at index i of the input string. This method
* is only meant for internal use.
* @param i The input string index to start matching at
* @return True if the input matched the expression
*/
protected boolean matchAt(int i)
{
// Initialize start pointer, paren cache and paren count
start0 = -1;
end0 = -1;
start1 = -1;
end1 = -1;
start2 = -1;
end2 = -1;
startn = null;
endn = null;
parenCount = 1;
setParenStart(0, i);
// Allocate backref arrays (unless optimizations indicate otherwise)
if ((program.flags & REProgram.OPT_HASBACKREFS) != 0)
{
startBackref = new int[maxParen];
endBackref = new int[maxParen];
}
// Match against string
int idx;
if ((idx = matchNodes(0, maxNode, i)) != -1)
{
setParenEnd(0, idx);
return true;
}
// Didn't match
parenCount = 0;
return false;
}
/**
* Matches the current regular expression program against a character array,
* starting at a given index.
* @param search String to match against
* @param i Index to start searching at
* @return True if string matched
*/
public boolean match(String search, int i)
{
return match(new StringCharacterIterator(search), i);
}
/**
* Matches the current regular expression program against a character array,
* starting at a given index.
* @param search String to match against
* @param i Index to start searching at
* @return True if string matched
*/
public boolean match(CharacterIterator search, int i)
{
// There is no compiled program to search with!
if (program == null)
{
// This should be uncommon enough to be an error case rather
// than an exception (which would have to be handled everywhere)
internalError("No RE program to run!");
}
// Save string to search
this.search = search;
// Can we optimize the search by looking for a prefix string?
if (program.prefix == null)
{
// Unprefixed matching must try for a match at each character
for ( ;! search.isEnd(i - 1); i++)
{
// Try a match at index i
if (matchAt(i))
{
return true;
}
}
return false;
}
else
{
// Prefix-anchored matching is possible
boolean caseIndependent = (matchFlags & MATCH_CASEINDEPENDENT) != 0;
char[] prefix = program.prefix;
for ( ;! search.isEnd(i + prefix.length - 1); i++)
{
// If the first character of the prefix matches
boolean match = false;
if (caseIndependent)
match = Character.toLowerCase(search.charAt(i)) == Character.toLowerCase(prefix[0]);
else
match = search.charAt(i) == prefix[0];
if (match)
{
// Save first character position
int firstChar = i++;
int k;
for (k = 1; k < prefix.length; )
{
// If there's a mismatch of any character in the prefix, give up
if (caseIndependent)
match = Character.toLowerCase(search.charAt(i++)) == Character.toLowerCase(prefix[k++]);
else
match = search.charAt(i++) == prefix[k++];
if (!match)
{
break;
}
}
// See if the whole prefix string matched
if (k == prefix.length)
{
// We matched the full prefix at firstChar, so try it
if (matchAt(firstChar))
{
return true;
}
}
// Match failed, reset i to continue the search
i = firstChar;
}
}
return false;
}
}
/**
* Matches the current regular expression program against a String.
* @param search String to match against
* @return True if string matched
*/
public boolean match(String search)
{
return match(search, 0);
}
/**
* Splits a string into an array of strings on regular expression boundaries.
* This function works the same way as the Perl function of the same name.
* Given a regular expression of "[ab]+" and a string to split of
* "xyzzyababbayyzabbbab123", the result would be the array of Strings
* "[xyzzy, yyz, 123]".
* @param s String to split on this regular exression
* @return Array of strings
*/
public String[] split(String s)
{
// Create new vector
Vector v = new Vector();
// Start at position 0 and search the whole string
int pos = 0;
int len = s.length();
// Try a match at each position
while (pos < len && match(s, pos))
{
// Get start of match
int start = getParenStart(0);
// Get end of match
int newpos = getParenEnd(0);
// Check if no progress was made
if (newpos == pos)
{
v.addElement(s.substring(pos, start + 1));
newpos++;
}
else
{
v.addElement(s.substring(pos, start));
}
// Move to new position
pos = newpos;
}
// Push remainder if it's not empty
String remainder = s.substring(pos);
if (remainder.length() != 0)
{
v.addElement(remainder);
}
// Return vector as an array of strings
String[] ret = new String[v.size()];
v.copyInto(ret);
return ret;
}
/**
* Flag bit that indicates that subst should replace all occurrences of this
* regular expression.
*/
public static final int REPLACE_ALL = 0x0000;
/**
* Flag bit that indicates that subst should only replace the first occurrence
* of this regular expression.
*/
public static final int REPLACE_FIRSTONLY = 0x0001;
/**
* Substitutes a string for this regular expression in another string.
* This method works like the Perl function of the same name.
* Given a regular expression of "a*b", a String to substituteIn of
* "aaaabfooaaabgarplyaaabwackyb" and the substitution String "-", the
* resulting String returned by subst would be "-foo-garply-wacky-".
* @param substituteIn String to substitute within
* @param substitution String to substitute for all matches of this regular expression.
* @return The string substituteIn with zero or more occurrences of the current
* regular expression replaced with the substitution String (if this regular
* expression object doesn't match at any position, the original String is returned
* unchanged).
*/
public String subst(String substituteIn, String substitution)
{
return subst(substituteIn, substitution, REPLACE_ALL);
}
/**
* Substitutes a string for this regular expression in another string.
* This method works like the Perl function of the same name.
* Given a regular expression of "a*b", a String to substituteIn of
* "aaaabfooaaabgarplyaaabwackyb" and the substitution String "-", the
* resulting String returned by subst would be "-foo-garply-wacky-".
* @param substituteIn String to substitute within
* @param substitution String to substitute for matches of this regular expression
* @param flags One or more bitwise flags from REPLACE_*. If the REPLACE_FIRSTONLY
* flag bit is set, only the first occurrence of this regular expression is replaced.
* If the bit is not set (REPLACE_ALL), all occurrences of this pattern will be
* replaced.
* @return The string substituteIn with zero or more occurrences of the current
* regular expression replaced with the substitution String (if this regular
* expression object doesn't match at any position, the original String is returned
* unchanged).
*/
public String subst(String substituteIn, String substitution, int flags)
{
// String to return
StringBuffer ret = new StringBuffer();
// Start at position 0 and search the whole string
int pos = 0;
int len = substituteIn.length();
// Try a match at each position
while (pos < len && match(substituteIn, pos))
{
// Append string before match
ret.append(substituteIn.substring(pos, getParenStart(0)));
// Append substitution
ret.append(substitution);
// Move forward, skipping past match
int newpos = getParenEnd(0);
// We always want to make progress!
if (newpos == pos)
{
newpos++;
}
// Try new position
pos = newpos;
// Break out if we're only supposed to replace one
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -