Java 改进基于正则表达式的替换性能
大家好,我想问一下进程所需的内存利用率和时间。我有以下代码。 我想优化我的代码,这样它会更快。 字符串将占用更多内存,有其他选择吗Java 改进基于正则表达式的替换性能,java,regex,string,performance,replaceall,Java,Regex,String,Performance,Replaceall,大家好,我想问一下进程所需的内存利用率和时间。我有以下代码。 我想优化我的代码,这样它会更快。 字符串将占用更多内存,有其他选择吗 public String replaceSingleToWord(String strFileText) { strFileText = strFileText.replaceAll("\\b(\\d+)[ ]?'[ ]?(\\d+)\"", "$1 feet $2 "); strFileText = strFileText.replaceAl
public String replaceSingleToWord(String strFileText) {
strFileText = strFileText.replaceAll("\\b(\\d+)[ ]?'[ ]?(\\d+)\"", "$1 feet $2 ");
strFileText = strFileText.replaceAll("\\b(\\d+)[ ]?'[ ]?(\\d+)''", "$1 feet $2 inch");
//for 23o34'
strFileText = strFileText.replaceAll("(\\d+)[ ]?(degree)+[ ]?(\\d+)'", "$1 degree $3 second");
strFileText = strFileText.replaceAll("(\\d+((,|.)\\d+)?)sq", " $1 sq");
strFileText = strFileText.replaceAll("(?i)(sq. Km.)", " sqkm");
strFileText = strFileText.replaceAll("(?i)(sq.[ ]?k.m.)", " sqkm");
strFileText = strFileText.replaceAll("(?i)\\s(lb.)", " pound");
//for pound
strFileText = strFileText.replaceAll("(?i)\\s(am|is|are|was|were)\\s?:", "$1 ");
return strFileText;
}
我想这将需要更多的内存和时间,我只是想降低复杂性。我只是想减少处理我需要做的更改的时间和内存。是否有替代replaceAll函数的方法?我将如何最小化此代码?这样,我的存储速度更快,内存利用率更低?在advanced中感谢您,当需要对字符串进行大量修改时,将使用StringBuffer和StringBuilder类 与字符串不同,StringBuffer和Stringbuilder类型的对象可以反复修改,而不会留下大量未使用的新对象 StringBuilder类是从Java5开始引入的,StringBuffer和StringBuilder之间的主要区别在于StringBuilder方法不是线程安全的(不同步) 建议尽可能使用StringBuilder,因为它比StringBuffer快。但是,如果需要线程安全,最好的选择是StringBuffer对象
public class Test{
public static void main(String args[]){
StringBuffer sBuffer = new StringBuffer(" test");
sBuffer.append(" String Buffer");
System.ou.println(sBuffer);
}
}
public class StringBuilderDemo {
public static void main(String[] args) {
String palindrome = "Dot saw I was Tod";
StringBuilder sb = new StringBuilder(palindrome);
sb.reverse(); // reverse it
System.out.println(sb);
}
}
因此,根据您的需要,您可以从tham中选择一种
参考当需要对字符串进行大量修改时,使用StringBuffer和StringBuilder类 与字符串不同,StringBuffer和Stringbuilder类型的对象可以反复修改,而不会留下大量未使用的新对象 StringBuilder类是从Java5开始引入的,StringBuffer和StringBuilder之间的主要区别在于StringBuilder方法不是线程安全的(不同步) 建议尽可能使用StringBuilder,因为它比StringBuffer快。但是,如果需要线程安全,最好的选择是StringBuffer对象
public class Test{
public static void main(String args[]){
StringBuffer sBuffer = new StringBuffer(" test");
sBuffer.append(" String Buffer");
System.ou.println(sBuffer);
}
}
public class StringBuilderDemo {
public static void main(String[] args) {
String palindrome = "Dot saw I was Tod";
StringBuilder sb = new StringBuilder(palindrome);
sb.reverse(); // reverse it
System.out.println(sb);
}
}
因此,根据您的需要,您可以从tham中选择一种
参考可以在点处改进正则表达式模式[,.]或
?
(而不是[]?
)
在函数外部使用编译的静态final模式
s
private static final Pattern PAT = Pattern.compile("...");
StringBuffer sb = new StringBuffer();
Matcher m = PAT.matcher(strFileText);
while (m.find()) {
m.appendReplacement(sb, "...");
}
m.appendTail(sb);
strFileText = sb.toString();
在执行
新的StringBuffer
之前,如果(m.find)进行第一次测试,则可以对正则表达式模式进行优化,可以在点处进行改进
在函数外部使用编译的静态final模式
s
private static final Pattern PAT = Pattern.compile("...");
StringBuffer sb = new StringBuffer();
Matcher m = PAT.matcher(strFileText);
while (m.find()) {
m.appendReplacement(sb, "...");
}
m.appendTail(sb);
strFileText = sb.toString();
在执行新StringBuffer
之前,可通过首次测试如果(m.find)
进行优化方法:
- 对每次替换使用
。创建一个类,创建模式字段,并只编译一次模式。这样可以节省大量时间,因为每次调用Pattern.compile()
时都会进行regex编译,而且这是一个非常昂贵的操作replaceAll()
- 使用非贪婪正则表达式。使用
代替(\\d+)
(\\d+?)
- 尽可能不要使用正则表达式(
->lb.
)lb
- 将具有相同替换的多个正则表达式合并为一个-适用于您的
或sqkm
替换feet
- 您可以尝试将api基于
;然后使用来处理文本StringBuilder
replace
s中的一个点是不可替换的。点匹配任何字符。使用\\.
课堂理念:
class RegexProcessor {
private Pattern feet1rep = Pattern.compile("\\b(\\d+)[ ]?'[ ]?(\\d+)\"");
// ...
public String process(String org) {
String mod = feet1rep.match(org).replaceAll("$1 feet $2 ");
/...
}
}
优化方法:
- 对每次替换使用
。创建一个类,创建模式字段,并只编译一次模式。这样可以节省大量时间,因为每次调用Pattern.compile()
时都会进行regex编译,而且这是一个非常昂贵的操作replaceAll()
- 使用非贪婪正则表达式。使用
代替(\\d+)
(\\d+?)
- 尽可能不要使用正则表达式(
->lb.
)lb
- 将具有相同替换的多个正则表达式合并为一个-适用于您的
或sqkm
替换feet
- 您可以尝试将api基于
;然后使用来处理文本StringBuilder
replace
s中的一个点是不可替换的。点匹配任何字符。使用\\.
课堂理念:
class RegexProcessor {
private Pattern feet1rep = Pattern.compile("\\b(\\d+)[ ]?'[ ]?(\\d+)\"");
// ...
public String process(String org) {
String mod = feet1rep.match(org).replaceAll("$1 feet $2 ");
/...
}
}
使用预编译模式和循环,就像Joop Eggen建议的那样。把你的表情组合在一起。例如,前两个可以写成
`"\\b(\\d++) ?' ?(\\d+)(?:''|\")"`
您可以以可读性损失为代价走得更远。也可以为所有替换项使用一个表达式
`"\\b(\\d++) ?(?:' ?(?:(\\d+)(?:''|\")|degree ?(\\d++)|...)"`
然后需要在组(2)==null
等条件下进行分支。这变得很难维护,但通过一个单循环和巧妙编写的正则表达式,您将赢得比赛D
诸如can't->canot,short't->short not等词的正则表达式是什么 这取决于你想要的精确程度。最简单的方法是
s.replaceAll(“\\Bn't\\b”,“not”)
。上述优化适用,因此在性能重要时,永远不要使用replaceAll
一般的解决方案可以是这样的
Pattern SHORTENED_WORD_PATTERN =
Pattern.compile("\\b(ca|should|wo|must|might)(n't)\\b");
String getReplacement(String trunk) {
switch (trunk) { // needs Java 7
case "wo": return "will not";
case "ca": return "cannot";
default: return trunk + " not";
}
}
... relevant part of the replacer loop (see [replaceAll][])
while (matcher.find()) {
matcher.appendReplacement(result, getReplacement(matcher.group(1)));
}
如果strFileText=strFileText.replace(“a”);strFileText=strFileText.replace™", "\'"); strFileText=strFileText.replace(“Ã、(”、“a”);strFileText=strFileText.replace(“o”);strFileText=strFileText.replace(“e”);strFileText=strFileText.replace(“e”);strFileText=strFileText.replace(“a”);strFileText=strFileText.replace(“c”);strFileText=strFileText.replace(“195”);如果我想用一行或另一行的方式来写,那么replaceach()更适合这种情况 如果要提高效率,请注意以上所有字符串都以相同的字符开头