如何在Java中实现通用文件加载器?
这就是我想做的:如何在Java中实现通用文件加载器?,java,Java,这就是我想做的: public String load(String path) { //... } load("file:/tmp/foo.txt"); // loads by absolute file name load("classpath:bar.txt"); // loads from classpath 我认为使用JDK是可能的,但不知道具体是如何实现的。从我的库omino Roundound,您需要的两种方法。。。我到处都需要它们。资源读取器是相对于类的,至少要知道要读取哪
public String load(String path) {
//...
}
load("file:/tmp/foo.txt"); // loads by absolute file name
load("classpath:bar.txt"); // loads from classpath
我认为使用JDK是可能的,但不知道具体是如何实现的。从我的库omino Roundound,您需要的两种方法。。。我到处都需要它们。资源读取器是相对于类的,至少要知道要读取哪个jar。但路径可以从/开始,以迫使其返回顶部。享受吧 (您必须制作我们自己的顶级包装器来查找“file:”和“classpath:”) 另见
公共静态字符串读取文件(字符串文件路径)
{
文件f=新文件(文件路径);
如果(!f.exists())
返回null;
字符串结果=”;
尝试
{
FileReader in=新的FileReader(f);
布尔doing=true;
char[]bunch=新字符[10000];
int-soFar=0;
边做
{
int got=in.read(bunch,0,bunch.length);
如果(得到我可以想到两种方法:
- 只需编写简单的Java代码,从类似URI的字符串中提取“scheme”,然后分派到不同的代码,以不同的方式加载文件
- 注册自定义URL流处理程序以处理“classpath”情况,然后使用
URL.openStream()
打开流以读取对象
的包文档中有一些关于如何发现流处理程序的信息。使用FileReader
或任何使用默认字符编码的方法都不是一个好主意。您对Unicode BOM奇怪行为的评论应该是一个提示,说明您没有正确处理编码。另外,为什么这两种方法都不正确相当长的方法的名字听起来好像他们做了类似的事情,但没有共享共同的逻辑?你可能想考虑他们都创建一个<代码>输入流< /代码>,然后他们传递给一个普通的私人助手方法。嗨,劳伦斯-谢谢你看,你的评论是很好的和赞赏。谢谢编码指针。关于共享内部助手方法的说明是有意义的。为什么它们现在是这样?它们是在不同的时间编写的,得到了大量的使用,而且,直到测试失败,我才注意到它。
public static String readFile(String filePath)
{
File f = new File(filePath);
if (!f.exists())
return null;
String result = "";
try
{
FileReader in = new FileReader(f);
boolean doing = true;
char[] bunch = new char[10000];
int soFar = 0;
while (doing)
{
int got = in.read(bunch, 0, bunch.length);
if (got <= 0)
doing = false;
else
{
String k = new String(bunch, 0, got);
result += k;
soFar += got;
}
}
} catch (Exception e)
{
return null;
}
// Strip off the UTF-8 front, if present. We hate this. EF BB BF
// see http://stackoverflow.com/questions/4897876/reading-utf-8-bom-marker for example.
// Mysteriously, when I read those 3 chars, they come in as 212,170,248. Fine, empirically, I'll strip that, too.
if(result != null && result.length() >= 3)
{
int c0 = result.charAt(0);
int c1 = result.charAt(1);
int c2 = result.charAt(2);
boolean leadingBom = (c0 == 0xEF && c1 == 0xBB && c2 == 0xBF);
leadingBom |= (c0 == 212 && c1 == 170 && c2 == 248);
if(leadingBom)
result = result.substring(3);
}
// And because I'm a dictator, fix up the line feeds.
result = result.replaceAll("\\r\\n", "\n");
result = result.replaceAll("\\r","\n");
return result;
}
static public String readResource(Class<?> aClass,String srcResourcePath)
{
if(aClass == null || srcResourcePath==null || srcResourcePath.length() == 0)
return null;
StringBuffer resultB = new StringBuffer();
URL resourceURL = null;
try
{
resourceURL = aClass.getResource(srcResourcePath);
}
catch(Exception e) { /* leave result null */ }
if(resourceURL == null)
return null; // sorry.
try
{
InputStream is = resourceURL.openStream();
final int BLOCKSIZE = 13007;
byte[] bytes = new byte[BLOCKSIZE];
int bytesRead = 0;
while(bytesRead >= 0)
{
bytesRead = is.read(bytes);
if(bytesRead > 0)
{
char[] chars = new char[bytesRead];
for(int i = 0; i < bytesRead; i++)
chars[i] = (char)bytes[i];
resultB.append(chars);
}
}
}
catch(IOException e)
{
return null; // sorry
}
String result = resultB.toString();
return result;
}