最近,我借助Tree
数据结构实现了电话簿。
我不仅在寻找可行的解决方案,而且还在寻找运行时和存储方面的最佳解决方案。
根据我的计算,需要N*log(T)
到add()
和get()
,其中N
是多个入口字符,T是每个节点的子代数目。 / p>
我可以解释一下我的想法:插入一个新名称后,需要花费一些时间才能在子Node
中找到一个具有相同字符的TreeMap = log(T)
,并且在N
次发生参数String
中的每个字符。
我对吗?
public final class PhoneBook {
private final Node name;
private final Node surname;
private final Comparator<Record> comparator;
public PhoneBook() {
this.name = new Node();
this.surname = new Node();
comparator = (r1, r2) -> {
int result = r1.getName().compareTo(r2.getName());
if (result == 0) {
result = r1.getSurname().compareTo(r2.getSurname());
if (result == 0) {
result = r1.getNumber().compareTo(r2.getNumber());
}
}
return result;
};
}
public void add(final Record record) {
add(record.getName().toLowerCase(), record, name);
add(record.getSurname().toLowerCase(), record, surname);
}
public SortedSet<Record> get(final String prefix) {
final String lc = prefix.toLowerCase();
final List<Record> recordsRetrievedByName = get(lc, name);
final List<Record> recordsRetrievedBySurname = get(lc, surname);
final SortedSet<Record> result = new TreeSet<>(comparator);
result.addAll(recordsRetrievedByName);
result.addAll(recordsRetrievedBySurname);
return result;
}
private List<Record> get(final String prefix, final Node ancestor) {
Node node = ancestor;
for (final char c: prefix.toCharArray()) {
final Node child = node.children.get(c);
if (child == null) {
return Collections.emptyList();
}
node = child;
}
return node.records;
}
private void add(final String str, final Record record, final Node ancestor) {
Node node = ancestor;
for (final char c: str.toCharArray()) {
final Node child;
if (node.children.containsKey(c)) {
child = node.children.get(c);
} else {
child = new Node();
node.children.put(c, child);
}
child.records.add(record);
node = child;
}
}
private static final class Node {
private final Map<Character, Node> children = new TreeMap<>();
private final List<Record> records = new ArrayList<>();
}
}
还有Record
不可变对象
public final class Record {
private final String name;
private final String surname;
private final String number;
//constructor, getters, toString
}