Java 使用带有变量的配置/属性文件
我使用这样一个简单的文本文件Java 使用带有变量的配置/属性文件,java,variables,configuration,import,configuration-files,Java,Variables,Configuration,Import,Configuration Files,我使用这样一个简单的文本文件 BMG-P (someLongComplicatedExpression)(.*P) BMG T (someLongComplicatedExpression)(.*[Tt]) BMG MPA (someLongComplicatedExpression)(.*MPA) 配置我的应用程序(使用bufferedReader.readLine().split(“\t”)进行简单导入)。困扰我的是冗余 我正在考虑这样的解决方案: %s=(someLongComp
BMG-P (someLongComplicatedExpression)(.*P)
BMG T (someLongComplicatedExpression)(.*[Tt])
BMG MPA (someLongComplicatedExpression)(.*MPA)
配置我的应用程序(使用bufferedReader.readLine().split(“\t”)
进行简单导入)。困扰我的是冗余
我正在考虑这样的解决方案:
%s=(someLongComplicatedExpression)
BMG-P %s(.*P)
BMG T %s(.*[Tt])
BMG MPA %s(.*MPA)
在这里,我读取变量的值(如%s),然后在导入后替换它们在字符串中的出现
我的问题是:
- 你知道哪些替代方法
- 在代码中替换变量的简单方法是什么
- 你能给我指出任何支持这种属性文件的框架吗
属性
类编写了这个简单的扩展:
import java.io.Serializable;
import java.util.Properties;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
/**
* Allows properties to contain expansions of the form ${propertyName}. This
* class makes no attempt to detect circular references, so be careful.
*/
public class ExpandingProperties extends Properties implements PropertySource {
private static final long serialVersionUID = 259782782423517925L;
private final Expander expander = new Expander();
@Override
public String getProperty(String key) {
return expander.expand(super.getProperty(key), this);
}
}
class Expander implements Serializable {
private static final long serialVersionUID = -2229337918353092460L;
private final Pattern pattern = Pattern.compile("\\$\\{([^}]+)\\}");
/**
* Expands variables of the form "${variableName}" within the
* specified string, using the property source to lookup the
* relevant value.
*/
public String expand(final String s, final PropertySource propertySource) {
if (s == null) {
return null;
}
final StringBuffer sb = new StringBuffer();
final Matcher matcher = pattern.matcher(s);
while (matcher.find()) {
final String variableName = matcher.group(1);
final String value = propertySource.getProperty(variableName);
if (value == null) {
throw new RuntimeException("No property found for: " + variableName);
}
matcher.appendReplacement(sb, value.replace("$", "\\$"));
}
matcher.appendTail(sb);
return sb.toString();
}
}
interface PropertySource {
String getProperty(String key);
}
用法示例:
public static void main(String[] args) {
Properties properties = new ExpandingProperties();
properties.put("myVar", "myLongExpression");
properties.put("foo", "${myVar}_1");
properties.put("bar", "${foo}_abc");
System.out.println(properties.getProperty("bar"));
}
印刷品:
myLongExpression_1_abc
由于ExpandingProperties
是Properties
的扩展,它继承了从属性文件加载值的所有load…()
方法
另一种方法是,它与上面的代码做了类似的事情,但更进一步,允许您嵌套属性文件等。我发现它对于我所需要的东西来说太过分了。我为Java
属性
类编写了这个简单的扩展:
import java.io.Serializable;
import java.util.Properties;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
/**
* Allows properties to contain expansions of the form ${propertyName}. This
* class makes no attempt to detect circular references, so be careful.
*/
public class ExpandingProperties extends Properties implements PropertySource {
private static final long serialVersionUID = 259782782423517925L;
private final Expander expander = new Expander();
@Override
public String getProperty(String key) {
return expander.expand(super.getProperty(key), this);
}
}
class Expander implements Serializable {
private static final long serialVersionUID = -2229337918353092460L;
private final Pattern pattern = Pattern.compile("\\$\\{([^}]+)\\}");
/**
* Expands variables of the form "${variableName}" within the
* specified string, using the property source to lookup the
* relevant value.
*/
public String expand(final String s, final PropertySource propertySource) {
if (s == null) {
return null;
}
final StringBuffer sb = new StringBuffer();
final Matcher matcher = pattern.matcher(s);
while (matcher.find()) {
final String variableName = matcher.group(1);
final String value = propertySource.getProperty(variableName);
if (value == null) {
throw new RuntimeException("No property found for: " + variableName);
}
matcher.appendReplacement(sb, value.replace("$", "\\$"));
}
matcher.appendTail(sb);
return sb.toString();
}
}
interface PropertySource {
String getProperty(String key);
}
用法示例:
public static void main(String[] args) {
Properties properties = new ExpandingProperties();
properties.put("myVar", "myLongExpression");
properties.put("foo", "${myVar}_1");
properties.put("bar", "${foo}_abc");
System.out.println(properties.getProperty("bar"));
}
印刷品:
myLongExpression_1_abc
由于ExpandingProperties
是Properties
的扩展,它继承了从属性文件加载值的所有load…()
方法
另一种方法是,它与上面的代码做了类似的事情,但更进一步,允许您嵌套属性文件等。我发现它对于我所需要的东西来说太过分了。看看这里:看看这里:第一眼,我喜欢它。懒散的扩展是个好主意。我想我可以在我的场景中使用它。我不理解PropertySource接口。你不是从属性继承的吗?接口有助于使其可测试(我可以模拟接口)。这也意味着扩展器不依赖于属性,可以在其他地方重用,并将其他对象用作PropertySource。但是,您不能传入java.util.Properties。对,您必须对其进行调整。我是一个端口和适配器的怪胎。也就是说,我尝试编写代码来使用和依赖“理想”接口,然后根据需要调整其他对象,以便它们呈现所需的接口。在本例中,
PropertySource
是使用字符串键获取单个字符串属性的“理想”接口,因此这就是Expander
所要求的。乍一看,我喜欢它。懒散的扩展是个好主意。我想我可以在我的场景中使用它。我不理解PropertySource接口。你不是从属性继承的吗?接口有助于使其可测试(我可以模拟接口)。这也意味着扩展器不依赖于属性,可以在其他地方重用,并将其他对象用作PropertySource。但是,您不能传入java.util.Properties。对,您必须对其进行调整。我是一个端口和适配器的怪胎。也就是说,我尝试编写代码来使用和依赖“理想”接口,然后根据需要调整其他对象,以便它们呈现所需的接口。在这种情况下,PropertySource
是使用字符串键获取单个字符串属性的“理想”接口,因此这就是Expander
所要求的。