[Java]_[初级]_[使用正则高效替换字符串的多个占位符为多个值]
Posted infoworld
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了[Java]_[初级]_[使用正则高效替换字符串的多个占位符为多个值]相关的知识,希望对你有一定的参考价值。
场景
- 在开发基于模板内容的
Java
程序时, 比如一个邮件内容模板,在内容里放置一些占位符$email
,$name
等来作为替换实际内容的符号。那么这时候如何做才可以少生成不必要的String
字符串,从而减少内存占用达到一次过替换完的目的呢?
说明
-
作为不可变字符串
String
,使用它的replace
方法替换会生成新的字符串,这个String
很明显不合适的,所以得使用可变字符串。 -
可变字符串使用
StringBuilder
或者StringBuffer
都可以.并且他们都有一个replace(start, end, str)和indexOf(str, fromIndex)
方法。这样的话最基本的做法就是indexOf
搜索到每个占位符,之后再替通过replace
这个方法来替换掉占位符。 -
具体的做法是使用一个新的
StringBuffer(StringBuilder)
作为临时存储, 搜索到的占位符添加到这个新的StringBuffer
里,其他非占位符也按顺序添加到这个StringBuffer
。最后这个StringBuffer
就可以作为新的替换后的字符串。 -
在
Java
的标准库里,使用Regex
正则可以简单实现上边的方案。就是通过Matcher
的appendReplacement
[1]方法添加不匹配的字符串和替代字符串,之后再用appendTail
添加剩余的不匹配字符串即可, 详细看例子. -
待解决问题:
Java
的正则没有找到可以设置多个值的办法.
例子
- 方法使用了一个
Map
来匹配符合的字符串,之后用关联的值来替换它。
package com.example.string;
import java.util.HashMap;
import java.util.Map;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import org.junit.jupiter.api.Test;
public class StringReplaceTest {
/**
*
* StringBuffer sb = new StringBuffer();
* HashMap<String, String> oldToNew = new HashMap<>();
* oldToNew.put("$sn",sn);
* oldToNew.put("$email",mail);
* StringUtils.replaceOneMore(sb,registertemplate,"[$]sn|[$]email",oldToNew);
*
* @param output
* @param input
* @param oldRegex
* @param oldToNew
*/
public static void replaceOneMore(StringBuffer output, String input,
String oldRegex, Map<String,String> oldToNew){
Pattern p = Pattern.compile(oldRegex);
Matcher m = p.matcher(input);
while (m.find()) {
String one = m.group();
if(oldToNew.containsKey(one))
m.appendReplacement(output, oldToNew.get(one));
}
m.appendTail(output);
}
public static<T> void print(String key,T t){
System.out.println(key +" : "+t);
}
@Test
public void testReplaceStringByRegexOrPredicate(){
StringBuffer sb = new StringBuffer();
HashMap<String, String> oldToNew = new HashMap<>();
oldToNew.put("$name","Tobey");
oldToNew.put("$email","test@gmail.com");
String registertemplate = "my name is $name, my email is $email, you can send to email to $email.";
replaceOneMore(sb,registertemplate,"[$]name|[$]email",oldToNew);
print("New String is: ",sb.toString());
}
}
输出
New String is: : my name is Tobey, my email is test@gmail.com, you can send to email to test@gmail.com.
参考
以上是关于[Java]_[初级]_[使用正则高效替换字符串的多个占位符为多个值]的主要内容,如果未能解决你的问题,请参考以下文章
[C/C++11]_[初级]_[使用正则表达式库regex]
[Java]_[初级]_[高效使用String.split的方法]
[Java]_[初级]_[高效使用String.split的方法]