首页 > 其他分享 >字符串插值替换器,替换字符串中的插值表达式(简单实现,仅用于短文本)

字符串插值替换器,替换字符串中的插值表达式(简单实现,仅用于短文本)

时间:2023-04-21 16:35:21浏览次数:37  
标签:replaceMap String 插值 rightText leftText replace content 字符串 替换

package com.geostar.geoonline.tools.config_write.util;

import lombok.Builder;
import lombok.Getter;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.regex.Pattern;

/**
 * 字符串插值替换器,替换字符串中的插值表达式(简单实现,仅用于短文本),如替换字符串“有一个人叫{{name}},他今年{{age}}岁,他在{{company}}上班”中双括号扩起来的内容
 */
@Getter
@Builder
public class StringReplacer {

    /**
     * 差值表达式左侧开始字符串,默认为 "{{"
     */
    private String leftText;

    /**
     * 差值表达式右侧结束字符串,默认为 "}}"
     */
    private String rightText;

    /**
     * 包含插值表达式的文本内容
     */
    private String content;

    /**
     * 严格模式,严格模式时调用 replace 方法 replaceMap 缺少替换参数则抛出异常
     */
    private boolean strict;

    public static void main(String[] args) {
        String content = "有一个人叫{{name}},他今年{{age}}岁,他在{{company}}上班";
        String leftText = "{{";
        String rightText = "}}";
        Map<String, String> replaceMap = new HashMap<>();
        replaceMap.put("name", "王睿");
        replaceMap.put("age", "34");
        replaceMap.put("company", "吉奥时空");
        String text = StringReplacer.builder()
                .content(content)
                .leftText(leftText)
                .rightText(rightText)
                .strict(true)
                .build().replace(replaceMap);
        System.out.println(text);
        System.out.println(StringReplacer.replace(content, leftText, rightText, replaceMap));
    }

    /**
     * 通过map替换
     *
     * @param replaceMap
     * @return
     */
    public String replace(Map<String, String> replaceMap) {
        if (leftText == null) {
            leftText = "{{";
        }
        if (rightText == null) {
            rightText = "}}";
        }
        return replace(content, leftText, rightText, replaceMap, strict);
    }

    public static String replace(String content, Map<String, String> replaceMap) {
        return replace(content, replaceMap, false);
    }

    public static String replace(String content, Map<String, String> replaceMap, boolean strict) {
        return replace(content, "{{", "}}", replaceMap, strict);
    }

    public static String replace(String content, String leftText, String rightText, Map<String, String> replaceMap) {
        return replace(content, leftText, rightText, replaceMap, false);
    }

    public static String replace(String content, String leftText, String rightText, Map<String, String> replaceMap, boolean strict) {
        checkProperties(content, leftText, rightText);
        List<Integer[]> replaceIndexList = getReplaceIndexList(content, leftText, rightText);
        StringBuilder sb = new StringBuilder();
        int endIndex = -1;
        for (int i = 0; i < replaceIndexList.size(); i++) {
            Integer[] integers = replaceIndexList.get(i);
            if (i == 0) {
                sb.append(content.substring(0, integers[0]));
            } else {
                Integer[] preIntegers = replaceIndexList.get(i - 1);
                sb.append(content.substring(preIntegers[1] + rightText.length(), integers[0]));
            }
            String key = content.substring(integers[0] + leftText.length(), integers[1]);
            if (!replaceMap.containsKey(key) || replaceMap.get(key) == null) {
                if (strict) {
                    throw new RuntimeException(String.format("replaceMap 不包含:%s,或其对应值为 null", key));
                } else {
                    sb.append(leftText + key + rightText);
                }
            } else {
                sb.append(replaceMap.get(key));
            }
            endIndex = integers[1];
        }
        sb.append(content.substring(endIndex + rightText.length(), content.length()));
        return sb.toString();
    }

    private static List<Integer[]> getReplaceIndexList(String content, String leftText, String rightText) {
        List<Integer[]> list = new ArrayList<>();
        List<Integer> leftTextIndex = getTextIndex(content, leftText);
        List<Integer> rightTextIndex = getTextIndex(content, rightText);
        int leftIndex = -1;
        int rightIndex = -1;
        for (int i = 0; i < content.length(); i++) {
            if (leftTextIndex.contains(i)) {
                leftIndex = i;
            }
            if (rightTextIndex.contains(i)) {
                rightIndex = i;
            }
            if (leftIndex != -1 && rightIndex != -1) {
                list.add(new Integer[]{leftIndex, rightIndex});
                leftIndex = -1;
                rightIndex = -1;
            }
        }
        return list;
    }

    private static List<Integer> getTextIndex(String content, String subtext) {
        if (!content.contains(subtext)) {
            return new ArrayList<>();
        }
        String[] split = content.split(Pattern.quote(subtext));
        List<Integer> list = new ArrayList<>();
        Integer index = 0;
        for (String s : split) {
            list.add(s.length() + index);
            index += s.length() + subtext.length();
        }
        list.remove(list.size() - 1);
        return list;
    }

    /**
     * 检测配置
     *
     * @param content
     * @param leftText
     * @param rightText
     */
    public static void checkProperties(String content, String leftText, String rightText) {
        if (content == null) {
            throw new RuntimeException("content 为空");
        }
        if (leftText == null || "".equals(leftText.trim()) || leftText.contains(" ")) {
            throw new RuntimeException("leftText 为空或包含空格");
        }
        if (rightText == null || "".equals(rightText.trim()) || rightText.contains(" ")) {
            throw new RuntimeException("rightText 为空或包含空格");
        }
    }

}

 

标签:replaceMap,String,插值,rightText,leftText,replace,content,字符串,替换
From: https://www.cnblogs.com/nihaorz/p/17340862.html

相关文章

  • C# 数组输出拼接字符串以及拼接字符串转数组
    staticvoidTest(){int[]arr=newint[]{1,2,3,4,5,6};stringstr=string.Join(",",arr);//数组转拼接字符串int[]arr_new=Array.ConvertAll(str.Split(','),p=>Convert.ToInt32(p));......
  • .NET实现解析字符串表达式
    一、引子·功能需求我们创建了一个School对象,其中包含了教师列表和学生列表。现在,我们需要计算教师平均年龄和学生平均年龄。//创建对象Schoolschool=newSchool(){Name="小菜学园",Teachers=newList<Teacher>(){newTeacher(){Name="波老......
  • 正则表达式获取字符串中电话号码的方式
    我一开始是想找数字1然后切出11位数字这样但是newbing给了一个简单了当的方法正则表达式直接切11位数字分享出来以供参考/***@Description:正则表达式寻找字符串中的电话号码*@paramstring有11位电话存在的字段*@author:@NewBing**/......
  • js 实现字符串反转
    1.情景展示在JavaScript当中,如何实现字符串倒转(倒置、反转)?2.具体分析数组Array实现元素倒转,有专门的函数reserve(),我们直接调用即可。为了使用这个功能,我们可以把字符串先拆分成数组,然后,再调用反转函数,最后再拼成字符串。3.解决方案以字符串:Marydon的博客园为例进行说明。......
  • [转]MySQL怎么将字符串转为datetime类型
    原文地址:https://zhuanlan.zhihu.com/p/553928079以前只知道第一种方法:方法1:使用str_to_date()函数str_to_date()是专门的字符串转日期函数,可以将字符串转换为日期时间值。str_to_date(str,format)str:必须项。要格式化为日期的字符串format:必须项。要使用的格式。例......
  • A - 简单字符串排序
    A- 简单字符串排序TimeLimit:5000MS     MemoryLimit:100000KB     64bitIOFormat:%lld&%lluSubmit StatusDescription从键盘输入10个学生的姓名和成绩,请按字典序排列学生的姓名并输出(姓名和成绩对应关系保持不变)。Input输入共11行,前10行......
  • 各位大神,我这代码,咋替换不成功?
    大家好,我是皮皮。一、前言前几天在Python白银交流群【崔艳飞】问了一个Pandas处理的问题,这里拿出来给大家分享下。二、实现过程这里【瑜亮老师】给了一个解决思路,如下图所示:顺利地解决了粉丝的问题。虽然有警告,但是不影响操作。三、总结大家好,我是皮皮。这篇文章主要......
  • 对比Python中的列表、元组、字典、集合、字符串等之间异同
    1.数据类型列表、元组、字典、集合、字符串均属于python3的标准数据类型。字符串和元组属于不可变数据,即创建后不可修改。列表、字典、集合属于可变数据,即创建后可以修改元素。2.创建有元素的对象3.创建没有元素的对象列表使用eval()或list()或中括号[]进行创建,元素之间使用逗号分......
  • 4/20 C语言判断字符串是否为回文,字符串中可以包含中文和英文
    //已知中文字符占用两个字节#include<stdio.h>#include<string.h>booljudge(char*a,int&i,int&k);intmain(){inti,k;chara[100];while(scanf("%s",a)!=EOF){i=0;k=strlen(a)-1;while......
  • 字符串string和STL总结
    设strings查找函数 1.a=s.find("me",a);以下标a开头查找字符串me找到了就返回下标到a找不到a就是-12.a=s.find(0,2,‘3’);在0到1内查找字符3找到了就返回下标到a找不到a就是-1 比较函数compares.compare(s.length()-4,3,"ong",0,3)以s.length()开头长度为3开始查找on......