整体架构设计
- 数据结构层:
- 使用
HashMap<String, List<Path>>
来存储文件名到文件路径的映射,用于按文件名检索。键为文件名,值为包含该文件名的文件路径列表。
- 对于按文件内容关键词检索,构建倒排索引结构。使用
HashMap<String, List<Path>>
,键为文件内容中的关键词,值为包含该关键词的文件路径列表。
- 索引构建层:
- 遍历指定目录及其子目录下的所有文件,使用
Files.walkFileTree
方法。
- 对于每个文件,提取文件名并添加到文件名索引中。
- 读取文件内容(对于文本文件,可以使用
Files.readAllLines
等方法),对内容进行分词处理(可以使用第三方分词工具如Lucene的分词器),将每个关键词添加到倒排索引中。
- 检索层:
- 提供方法接收检索关键词,根据检索类型(文件名或文件内容)从相应的索引结构中获取文件路径列表。
核心算法
- 索引构建算法:
- 输入:文件目录路径
- 步骤:
- 初始化文件名索引
HashMap<String, List<Path>> fileNameIndex
和文件内容关键词倒排索引HashMap<String, List<Path>> contentIndex
。
- 使用
Files.walkFileTree
遍历目录,对于每个文件:
- 将文件名添加到
fileNameIndex
中。
- 读取文件内容,分词后将每个关键词添加到
contentIndex
中。
- 检索算法:
- 输入:检索关键词,检索类型(文件名或文件内容)
- 步骤:
- 根据检索类型选择相应的索引(文件名索引或文件内容关键词倒排索引)。
- 从索引中获取包含检索关键词的文件路径列表。
关键代码示例
import java.io.IOException;
import java.nio.file.*;
import java.util.*;
public class FileIndexSystem {
private Map<String, List<Path>> fileNameIndex;
private Map<String, List<Path>> contentIndex;
public FileIndexSystem() {
fileNameIndex = new HashMap<>();
contentIndex = new HashMap<>();
}
// 构建索引
public void buildIndex(Path directory) throws IOException {
Files.walkFileTree(directory, new SimpleFileVisitor<Path>() {
@Override
public FileVisitResult visitFile(Path file, BasicFileAttributes attrs) throws IOException {
// 处理文件名索引
String fileName = file.getFileName().toString();
fileNameIndex.putIfAbsent(fileName, new ArrayList<>());
fileNameIndex.get(fileName).add(file);
// 处理文件内容索引(假设为文本文件)
if (Files.probeContentType(file).startsWith("text")) {
List<String> lines = Files.readAllLines(file);
for (String line : lines) {
String[] words = line.split("\\s+");
for (String word : words) {
contentIndex.putIfAbsent(word, new ArrayList<>());
contentIndex.get(word).add(file);
}
}
}
return FileVisitResult.CONTINUE;
}
});
}
// 按文件名检索
public List<Path> searchByFileName(String fileName) {
return fileNameIndex.getOrDefault(fileName, Collections.emptyList());
}
// 按文件内容关键词检索
public List<Path> searchByContent(String keyword) {
return contentIndex.getOrDefault(keyword, Collections.emptyList());
}
}
使用示例
public class Main {
public static void main(String[] args) {
try {
FileIndexSystem indexSystem = new FileIndexSystem();
Path directory = Paths.get("your_directory_path");
indexSystem.buildIndex(directory);
List<Path> byFileName = indexSystem.searchByFileName("example.txt");
System.out.println("By File Name: " + byFileName);
List<Path> byContent = indexSystem.searchByContent("keyword");
System.out.println("By Content: " + byContent);
} catch (IOException e) {
e.printStackTrace();
}
}
}
保证系统的高效性和扩展性
- 高效性:
- 索引结构:使用
HashMap
作为索引结构,其查找操作的时间复杂度为O(1)平均情况,能够快速定位文件路径。
- 并行处理:在构建索引时,可以考虑使用Java的并行流对文件进行并行处理,加快索引构建速度。例如,
Files.walk(directory).parallel().forEach(file -> { /* 索引构建操作 */ });
。
- 扩展性:
- 模块化设计:将索引构建、检索等功能模块化,方便替换或扩展具体实现。例如,如果需要更复杂的文件内容处理,可以将文件内容读取和分词部分封装成独立的模块,方便更换为更强大的分词工具。
- 支持更多检索类型:可以在现有架构基础上,通过添加新的索引结构和检索逻辑,支持更多的检索方式,如按文件大小、修改时间等检索。