如何使用 Java 属性文件?
Posted
技术标签:
【中文标题】如何使用 Java 属性文件?【英文标题】:How to use Java property files? 【发布时间】:2010-11-22 01:06:18 【问题描述】:我有一个配置值的键/值对列表,我想将其存储为 Java 属性文件,然后加载和迭代。
问题:
我是否需要将文件存储在与加载它们的类相同的包中,或者是否有任何特定的位置应该放置它? 文件是否需要以任何特定扩展名结尾或者是.txt
OK?
如何在代码中加载文件
我如何遍历里面的值?
【问题讨论】:
【参考方案1】:您可以将 InputStream 传递给属性,因此您的文件几乎可以在任何地方,并且可以调用任何东西。
Properties properties = new Properties();
try
properties.load(new FileInputStream("path/filename"));
catch (IOException e)
...
迭代为:
for(String key : properties.stringPropertyNames())
String value = properties.getProperty(key);
System.out.println(key + " => " + value);
【讨论】:
属性文件中不存在键时返回什么值? @MitakshGupta 如果在文件或默认属性列表中找不到具有您传递的名称的属性,则返回null
。见Javadoc
这与properties.load(PropertiesReader.class.getResourceAsStream("/properties.properties"));
(即getResourceAsStream
与FileInputStream
)相比如何?利弊?
不关闭FileInputStream有问题吗?【参考方案2】:
您可以将文件存储在您喜欢的任何位置。如果你想将它保存在你的 jar 文件中,你需要使用Class.getResourceAsStream()
或ClassLoader.getResourceAsStream()
来访问它。如果它在文件系统上,它会稍微容易一些。
任何扩展都可以,尽管 .properties 在我的经验中更常见
使用Properties.load
加载文件,如果您使用的是Java 6,则传入InputStream
或StreamReader
。(如果您正在使用Java 6,我' d 可能对流使用 UTF-8 和 Reader
,而不是默认的 ISO-8859-1 编码。)
像遍历普通的Hashtable
(Properties
派生自)一样遍历它,例如使用keySet()
。或者,您可以使用propertyNames()
返回的枚举。
【讨论】:
谢谢乔恩,接下来我知道我会在 joda 上查找一些内容,你也会回答这个问题。【参考方案3】:如果你把属性文件和类Foo放在同一个包中,你可以很容易地用它来加载它
new Properties().load(Foo.class.getResourceAsStream("file.properties"))
鉴于 Properties 扩展了 Hashtable,您可以像在 Hashtable 中那样迭代值。
如果您使用 *.properties 扩展名,您可以获得编辑器支持,例如Eclipse 有一个属性文件编辑器。
【讨论】:
你可以这样做 - 但我不喜欢将属性文件存储在同一个包中。您最终会得到分布在应用程序中各处的属性文件。我更愿意将所有属性文件存储在应用程序的根目录中,并将它们加载为“class.getResourceAsStream("\file.properties")”或其他一些已知位置。 内特,这是真的。但是,在某些情况下,部署位置是未知的(例如,您的特定组件的所有内容都捆绑到某个存档中)。在这种情况下,可以很方便地说“它在那个类中,无论那个类最终在哪里”。此外,为了避免文件分散,可以将单个配置包用于所有属性文件。 F***,这两种情况都适用于我的评论 - 它基于类路径 - 而不是文件系统。 对于任何试图让 Nate 的示例工作的人 - 应该用正斜杠替换反斜杠。所以在这种情况下:'class.getResourceAsStream("/file.properties")'【参考方案4】:有很多方法可以创建和读取properties
文件:
-
将文件存储在同一个包中。
推荐
.properties
扩展,但您可以选择自己的。
使用位于java.util
package => Properties
、ListResourceBundle
、ResourceBundle
classes 的这些类。
要读取属性,请使用 Properties
或 java.lang.System
类的迭代器或枚举器或直接方法。
ResourceBundle
类:
ResourceBundle rb = ResourceBundle.getBundle("prop"); // prop.properties
System.out.println(rb.getString("key"));
Properties
类:
Properties ps = new Properties();
ps.Load(new java.io.FileInputStream("my.properties"));
【讨论】:
嗨 AVD,为什么我们只需要.properties
扩展? '.txt' 扩展有什么问题?请帮助我。
@atishshimpi 在使用 Properties 类型时不需要,但对于 ResourceBundle 是必需的 - 阅读文档-docs.oracle.com/javase/8/docs/api/java/util/ResourceBundle.html【参考方案5】:
这会加载属性文件:
Properties prop = new Properties();
InputStream stream = ...; //the stream to the file
try
prop.load(stream);
finally
stream.close();
我习惯把.properties文件放在一个我有所有配置文件的目录下,我没有把它和访问它的类放在一起,但是这里没有限制。
对于名称...为了冗长,我使用 .properties,如果您不想要,我认为您不应该将其命名为 .properties。
【讨论】:
但是,一些属性文件的“扩展”假定使用 .properties 扩展 - 例如 I18N 中使用的 ResourceBundle。【参考方案6】:属性已成为遗产。 Preferences 类优于属性。
偏好数据的分层集合中的一个节点。此类允许应用程序存储和检索用户和系统首选项和配置数据。此数据永久存储在依赖于实现的后备存储中。典型的实现包括平面文件、特定于操作系统的注册表、目录服务器和 SQL 数据库。这个类的用户不需要关心后备存储的细节。
与基于字符串的键值对的属性不同,Preferences
类有多种方法用于获取原始数据并将其放入 Preferences 数据存储中。我们只能使用以下类型的数据:
-
字符串
布尔值
双
浮动
int
长
字节数组
要加载属性文件,您可以提供绝对路径,或者如果属性文件存在于您的类路径中,则使用getResourceAsStream()
。
package com.mypack.test;
import java.io.*;
import java.util.*;
import java.util.prefs.Preferences;
public class PreferencesExample
public static void main(String args[]) throws FileNotFoundException
Preferences ps = Preferences.userNodeForPackage(PreferencesExample.class);
// Load file object
File fileObj = new File("d:\\data.xml");
try
FileInputStream fis = new FileInputStream(fileObj);
ps.importPreferences(fis);
System.out.println("Prefereces:"+ps);
System.out.println("Get property1:"+ps.getInt("property1",10));
catch (Exception err)
err.printStackTrace();
xml 文件:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE preferences SYSTEM 'http://java.sun.com/dtd/preferences.dtd'>
<preferences EXTERNAL_XML_VERSION="1.0">
<root type="user">
<map />
<node name="com">
<map />
<node name="mypack">
<map />
<node name="test">
<map>
<entry key="property1" value="80" />
<entry key="property2" value="Red" />
</map>
</node>
</node>
</node>
</root>
</preferences>
看看这个article的偏好商店内部
【讨论】:
【参考方案7】:例子:
Properties pro = new Properties();
FileInputStream in = new FileInputStream("D:/prop/prop.properties");
pro.load(in);
String temp1[];
String temp2[];
// getting values from property file
String username = pro.getProperty("usernamev3");//key value in prop file
String password = pro.getProperty("passwordv3");//eg. username="zub"
String delimiter = ","; //password="abc"
temp1=username.split(delimiter);
temp2=password.split(delimiter);
【讨论】:
如果你有 3 个属性文件怎么办?【参考方案8】:按顺序:
-
您几乎可以将文件存储在任何地方。
无需扩展。
Montecristo 有illustrated 如何加载这个。这应该可以正常工作。
propertyNames() 为您提供了一个可迭代的枚举。
【讨论】:
2. no extension is necessary
,请您提供此声明的任何参考。我对此感到困惑。
请注意,您可以通过输入流加载属性。因此,属性不知道输入流来自哪里(文件?套接字?),因此无法强制执行命名标准【参考方案9】:
默认情况下,Java 在应用程序的工作目录中打开它(此行为实际上取决于所使用的操作系统)。要加载文件,请执行以下操作:
Properties props = new java.util.Properties();
FileInputStream fis new FileInputStream("myfile.txt");
props.load(fis)
因此,任何文件扩展名都可以用于属性文件。此外,该文件也可以存储在任何地方,只要您可以使用FileInputStream
。
在相关说明中,如果您使用现代框架,该框架可能会提供打开属性文件的其他方式。例如,Spring 提供了ClassPathResource
来使用 JAR 文件中的包名加载属性文件。
至于遍历属性,一旦加载了属性,它们就会存储在java.util.Properties
对象中,该对象提供propertyNames()
方法。
【讨论】:
【参考方案10】:读取属性文件并将其内容加载到Properties
String filename = "sample.properties";
Properties properties = new Properties();
input = this.getClass().getClassLoader().getResourceAsStream(filename);
properties.load(input);
以下是迭代Properties
的有效方法
for (Entry<Object, Object> entry : properties.entrySet())
System.out.println(entry.getKey() + " => " + entry.getValue());
【讨论】:
【参考方案11】:在 Java 8 中获取所有属性
public static Map<String, String> readPropertiesFile(String location) throws Exception
Map<String, String> properties = new HashMap<>();
Properties props = new Properties();
props.load(new FileInputStream(new File(location)));
props.forEach((key, value) ->
properties.put(key.toString(), value.toString());
);
return properties;
【讨论】:
【参考方案12】:1) 最好将属性文件放在类路径中,但您可以将它放在项目中的任何位置。
以下是如何从类路径加载属性文件并读取所有属性。
Properties prop = new Properties();
InputStream input = null;
try
String filename = "path to property file";
input = getClass().getClassLoader().getResourceAsStream(filename);
if (input == null)
System.out.println("Sorry, unable to find " + filename);
return;
prop.load(input);
Enumeration<?> e = prop.propertyNames();
while (e.hasMoreElements())
String key = (String) e.nextElement();
String value = prop.getProperty(key);
System.out.println("Key : " + key + ", Value : " + value);
catch (IOException ex)
ex.printStackTrace();
finally
if (input != null)
try
input.close();
catch (IOException e)
e.printStackTrace();
2) 属性文件的扩展名为 .properties
【讨论】:
【参考方案13】:这是遍历属性的另一种方法:
Enumeration eProps = properties.propertyNames();
while (eProps.hasMoreElements())
String key = (String) eProps.nextElement();
String value = properties.getProperty(key);
System.out.println(key + " => " + value);
【讨论】:
我很抱歉。我查看了 Zed 答案中的代码,它运行良好......我不知道当时我的想法......实际上他的解决方案比我的更好,我认为......【参考方案14】:去年我写过关于这个属性框架的文章。 它将提供多种加载属性的方法,并具有强类型。
看看http://sourceforge.net/projects/jhpropertiestyp/
JHPropertiesTyped 将为开发人员提供强类型属性。 易于集成到现有项目中。 由大量的属性类型处理。 提供通过属性 IO 实现单行初始化属性的能力。 使开发人员能够创建自己的属性类型和属性 io。 网络演示也可用,如上图所示。 如果您选择使用它,还有一个用于管理属性的 Web 前端的标准实现。
项目网页上提供了完整的文档、教程、javadoc、faq 等。
【讨论】:
【参考方案15】:这里准备好了静态类
import java.io.*;
import java.util.Properties;
public class Settings
public static String Get(String name,String defVal)
File configFile = new File(Variables.SETTINGS_FILE);
try
FileReader reader = new FileReader(configFile);
Properties props = new Properties();
props.load(reader);
reader.close();
return props.getProperty(name);
catch (FileNotFoundException ex)
// file does not exist
logger.error(ex);
return defVal;
catch (IOException ex)
// I/O error
logger.error(ex);
return defVal;
catch (Exception ex)
logger.error(ex);
return defVal;
public static Integer Get(String name,Integer defVal)
File configFile = new File(Variables.SETTINGS_FILE);
try
FileReader reader = new FileReader(configFile);
Properties props = new Properties();
props.load(reader);
reader.close();
return Integer.valueOf(props.getProperty(name));
catch (FileNotFoundException ex)
// file does not exist
logger.error(ex);
return defVal;
catch (IOException ex)
// I/O error
logger.error(ex);
return defVal;
catch (Exception ex)
logger.error(ex);
return defVal;
public static Boolean Get(String name,Boolean defVal)
File configFile = new File(Variables.SETTINGS_FILE);
try
FileReader reader = new FileReader(configFile);
Properties props = new Properties();
props.load(reader);
reader.close();
return Boolean.valueOf(props.getProperty(name));
catch (FileNotFoundException ex)
// file does not exist
logger.error(ex);
return defVal;
catch (IOException ex)
// I/O error
logger.error(ex);
return defVal;
catch (Exception ex)
logger.error(ex);
return defVal;
public static void Set(String name, String value)
File configFile = new File(Variables.SETTINGS_FILE);
try
Properties props = new Properties();
FileReader reader = new FileReader(configFile);
props.load(reader);
props.setProperty(name, value.toString());
FileWriter writer = new FileWriter(configFile);
props.store(writer, Variables.SETTINGS_COMMENT);
writer.close();
catch (FileNotFoundException ex)
// file does not exist
logger.error(ex);
catch (IOException ex)
// I/O error
logger.error(ex);
catch (Exception ex)
logger.error(ex);
public static void Set(String name, Integer value)
File configFile = new File(Variables.SETTINGS_FILE);
try
Properties props = new Properties();
FileReader reader = new FileReader(configFile);
props.load(reader);
props.setProperty(name, value.toString());
FileWriter writer = new FileWriter(configFile);
props.store(writer,Variables.SETTINGS_COMMENT);
writer.close();
catch (FileNotFoundException ex)
// file does not exist
logger.error(ex);
catch (IOException ex)
// I/O error
logger.error(ex);
catch (Exception ex)
logger.error(ex);
public static void Set(String name, Boolean value)
File configFile = new File(Variables.SETTINGS_FILE);
try
Properties props = new Properties();
FileReader reader = new FileReader(configFile);
props.load(reader);
props.setProperty(name, value.toString());
FileWriter writer = new FileWriter(configFile);
props.store(writer,Variables.SETTINGS_COMMENT);
writer.close();
catch (FileNotFoundException ex)
// file does not exist
logger.error(ex);
catch (IOException ex)
// I/O error
logger.error(ex);
catch (Exception ex)
logger.error(ex);
这里是示例:
Settings.Set("valueName1","value");
String val1=Settings.Get("valueName1","value");
Settings.Set("valueName2",true);
Boolean val2=Settings.Get("valueName2",true);
Settings.Set("valueName3",100);
Integer val3=Settings.Get("valueName3",100);
【讨论】:
【参考方案16】:您可以通过以下方式加载属性文件:
InputStream is = new Test().getClass().getClassLoader().getResourceAsStream("app.properties");
Properties props = new Properties();
props.load(is);
然后您可以使用如下 lambda 表达式遍历地图:
props.stringPropertyNames().forEach(key ->
System.out.println("Key is :"+key + " and Value is :"+props.getProperty(key));
);
【讨论】:
【参考方案17】:在我看来,当我们可以很简单地做到这一点时,其他方式已被弃用,如下所示:
@PropertySource("classpath:application.properties")
public class SomeClass
@Autowired
private Environment env;
public void readProperty()
env.getProperty("language");
它是如此简单,但我认为这是最好的方法! 享受
【讨论】:
以上是关于如何使用 Java 属性文件?的主要内容,如果未能解决你的问题,请参考以下文章
如何在 JAVA 中使用 ResourceBundle 将匈牙利字符作为属性文件中的键?