【发布时间】:2016-07-27 17:13:49
【问题描述】:
存储电话簿联系人的最佳数据结构是什么,每个联系人都由名字、姓氏和电话号码组成。用户必须能够按每个字段进行搜索。 有类似的问题,但没有一个答案足够清楚。
【问题讨论】:
-
我会说使用哈希表,但这确实是您所习惯的。
-
所有电话号码都是美国的还是会有那些格式奇怪的非美国号码?
标签: java data-structures
存储电话簿联系人的最佳数据结构是什么,每个联系人都由名字、姓氏和电话号码组成。用户必须能够按每个字段进行搜索。 有类似的问题,但没有一个答案足够清楚。
【问题讨论】:
标签: java data-structures
创建一个 POJO 类型,用于存储名字、姓氏和电话号码(如果需要,可以使其可变)。
class PhoneBookEntry {
public final String firstName;
public final String lastName;
public final String phoneNumber;
public Entry(String firstName, String lastName, String phoneNumber) {
this.firstName = firstName;
this.lastName = lastName;
this.phoneNumber = phoneNumber;
}
//... equals + hashcode implementation
}
您可以像这样创建您的电话簿:
class PhoneBook {
private Map<String, Set<PhoneBookEntry>> firstNameMap;
private Map<String, Set<PhoneBookEntry>> lastNameMap;
private Map<String, Set<PhoneBookEntry>> phoneNumberMap;
public void add(PhoneBookEntry entry) {
Set<PhoneBookEntry> set
= firstNameMap.computeIfAbsent(entry.firstName, k -> new HashSet<>());
set.add(entry);
set = lastNameMap.computeIfAbsent(entry.lastName, k -> new HashSet<>());
set.add(entry);
set = phoneNumberMap.computeIfAbsent(entry.phoneNumber, k -> new HashSet<>());
set.add(entry);
}
public Set<PhoneBookEntry> getByFirstName(String firstName) {
return firstNameMap.get(firstName);
}
public Set<PhoneBookEntry> getByLastName(String lastName) {
return lastNameMap.get(lastName);
}
public Set<PhoneBookEntry> getByPhoneNumber(String phoneNumber) {
return phoneNumberMap.get(phoneNumber);
}
}
使用Maps 可以快速查找。
正如 yitzih 所说,多个联系人可以有相同的名字、姓氏或电话号码。因此,按名字查找(例如)将返回一组联系人。
【讨论】:
创建一个联系人对象,该对象存储每个联系人所需的变量。使用 ArrayList 来存储它们。
如果没有关于联系人的更多信息,实际上没有任何方法可以使用 HashTable、Map 或 Graph。 HashTable 没有真正的键值对,除非你想使用名字和姓氏的组合,但是你需要一些方法来处理冲突(如果两个人的名字完全相同),或者你需要禁止有 2 个人具有相同的联系人姓名(但您为什么要这样做?)
【讨论】:
Class Contact{
String forename;
String Surname;
String phoneNo;
public Contact(fName, sName, pNo){
forename = fName;
Surname = sName;
phoneNo = pNo;
}
public String getForename(){}
public String getSurname(){}
public String getPhoneNo(){}
}
在处理搜索的类中, 你声明一个 Contact 类型的 arrayList,当搜索一个联系人时说 John,
public Contact searchContact(String s){
for(int i = 0; i< ContactList.size(); i++){
if(ContactList.get(i).getForename().equals(s) ||
ContactList.get(i).getSurame().equals(s) ||
ContactList.get(i).getPhoneNo().equals(s)
){
return ContactList.get(i);
}
}
return null;
}
【讨论】:
有点模糊的问题,但到底是什么,也许这会赶走我午饭后的困倦。我假设电话号码的简单字符串表示,但最好的数据对象存储所有可能的世界电话号码种类以及智能搜索它们的方法(例如“(123)456-7891”与“1234567891”?)可能完全是它自己的问题。
这里的电话簿类存储了所有的联系人。 searchFirst()、searchLast() 和 searchPhoneNumber() 方法分别返回匹配联系人的列表。
public class PhoneBook {
ArrayList<Contact> contacts;
public PhoneBook() {
contacts = new ArrayList<>();
}
public void addContact(Contact contact) {
contacts.add(contact);
}
public ArrayList<Contact> searchFirst(String first) {
ArrayList<Contact> foundContacts = new ArrayList<>();
for (Contact contact: contacts) {
if (contact.first.equals(first)) {
foundContacts.add(contact);
}
}
return foundContacts;
}
public ArrayList<Contact> searchLast(String last) {
ArrayList<Contact> foundContacts = new ArrayList<>();
for (Contact contact: contacts) {
if (contact.last.equals(last)) {
foundContacts.add(contact);
}
}
return foundContacts;
}
public ArrayList<Contact> searchPhoneNumber(String phoneNumber) {
ArrayList<Contact> foundContacts = new ArrayList<>();
for (Contact contact: contacts) {
if (contact.phoneNumber.equals(phoneNumber)) {
foundContacts.add(contact);
}
}
return foundContacts;
}
class Contact {
String first;
String last;
String phoneNumber;
public Contact(String first, String last, String phoneNumber) {
this.first = first;
this.last = last;
this.phoneNumber = phoneNumber;
}
}
}
【讨论】: