Implement binary search in objects

左心房为你撑大大i 提交于 2019-11-27 03:35:53

The Object Ordering article of The Java Tutorials has an example of writing your own Comparator in order to perform comparisons on custom types.

Then, the ArrayList (or any other List), the key to find, along with Comparator can be passed into the Collections.binarySearch method.

Here's an example:

import java.util.*;

class BinarySearchWithComparator
{
  public static void main(String[] args)
  {
    // Please scroll down to see 'User' class implementation.
    List<User> l = new ArrayList<User>();
    l.add(new User(10, "A"));
    l.add(new User(20, "B"));
    l.add(new User(30, "C"));

    Comparator<User> c = new Comparator<User>() {
      public int compare(User u1, User u2) {
        return u1.getId().compareTo(u2.getId());
      }
    };

    // Must pass in an object of type 'User' as the key.
    // The key is an 'User' with the 'id' which is been searched for.
    // The 'name' field is not used in the comparison for the binary search,
    // so it can be a dummy value -- here it is omitted with a null.
    //
    // Also note that the List must be sorted before running binarySearch,
    // in this case, the list is already sorted.

    int index = Collections.binarySearch(l, new User(20, null), c);
    System.out.println(index);    // Output: 1

    index = Collections.binarySearch(l, new User(10, null), c);
    System.out.println(index);    // Output: 0

    index = Collections.binarySearch(l, new User(42, null), c);
    System.out.println(index);    // Output: -4
                                  // See javadoc for meaning of return value.
  }
}

class User {
  private int id;
  private String name;

  public User(int id, String name) {
    this.id = id;
    this.name = name;
  }

  public Integer getId() {
    return Integer.valueOf(id);
  }
}

You could also put the comparator in the User class:

public class User implements Comparable<User>, Comparator<User>
{
  public User(int id, String name)
  {
    this.id = id;
    this.name = name;
  }
  @Override
  public int compareTo(User u)
  {
    return id - u.getID();
  }
  @Override
  public int compare(User u1, User u2)
  {
    return u1.getID() - u2.getID();
  }

  public int getID() { return id; }
  public String getName() { return name; }
  private int id;
  private String name;
}

Then you would do the following to an ArrayList called users:

ArrayList<User> users = new ArrayList<User>();
users.add(new User(3, "Fred"));
users.add(new User(42, "Joe"));
users.add(new User(5, "Mary"));
users.add(new User(17, "Alice"));

Collections.sort(users);
int index = Collections.binarySearch(users, new User(5, null));
if(index >= 0)
  System.out.println("The user name of id 5 is: "+users.get(index).getName());
else
  System.out.println("ID 5 is not in the list");

Use Collections.binarySearch with a Comparator.

import java.util.Collections;
Collections.binarySearch(users, id);

You should use binarySearch method only on the sorted ArrayList. so First sort the ArraList and use the same comparator reference (which you used to do the sort) to perform the binarySearch operation.

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!