Java 中的 HashMap 和 TreeMap

        HashMap和TreeMap是集合框架的一部分。HashMap java.util.HashMap 类是基于 Hashing 的实现。在 HashMap 中,我们有一个键和一个值对 <Key, Value> 。

        HashMap<K,V> hmap = new HashMap<K,V>();

让我们考虑下面的例子,我们必须计算给定整数数组中每个整数的出现次数。

输入:arr[] = {10, 3, 5, 10, 3, 5, 10};

输出:频率 10 是 3
        3 的频率是 2
        5 的频率是 2

例子:

/* Java program to print frequencies of all elements using 
   HashMap */
import java.util.*;
 
class Main
{
    // This function prints frequencies of all elements
    static void printFreq(int arr[])
    {
        // Creates an empty HashMap
        HashMap<Integer, Integer> hmap = 
                     new HashMap<Integer, Integer>();
 
        // Traverse through the given array
        for (int i = 0; i < arr.length; i++)
        {
            Integer c = hmap.get(arr[i]);
 
            // If this is first occurrence of element 
            if (hmap.get(arr[i]) == null)
               hmap.put(arr[i], 1);
 
            // If elements already exists in hash map
            else
              hmap.put(arr[i], ++c);
        }
 
        // Print result
        for (Map.Entry m:hmap.entrySet())
          System.out.println("Frequency of " + m.getKey() + 
                             " is " + m.getValue());
    }
 
    // Driver method to test above method
    public static void main (String[] args)
    {
        int arr[] = {10, 34, 5, 10, 3, 5, 10};
        printFreq(arr);
    }
}

输出:

34 的频率为 1 
3 的频率为 1 
5 的频率为 2 
10 的频率为 3

关键点

    1、HashMap 不维护任何基于键或基于值的顺序,如果我们希望按排序顺序维护键,我们需要使用 TreeMap。

    2、复杂性:get/put/containsKey() 操作在平均情况下是 O(1),但我们不能保证这一点,因为这完全取决于计算哈希值所需的时间。

应用: HashMap 基本上是哈希的一种实现。因此,只要我们需要使用键值对进行哈希处理,我们就可以使用 HashMap。例如,在 Web 应用程序中,用户名作为键存储,用户数据作为值存储在 HashMap 中,以便更快地检索与用户名相对应的用户数据。  

        TreeMap当我们只需要按排序顺序存储唯一元素时,TreeMap 会非常方便。Java.util.TreeMap 在后台使用红黑树,以确保没有重复项;此外,它还按排序顺序维护元素。

TreeMap<K, V> hmap = new TreeMap<K, V>();

        下面是基于 TreeMap 的相同问题的实现。与之前的 O(n) 解决方案相比,此解决方案的时间复杂度更高,为 O(nLogn)。此方法的优点是,我们可以按排序顺序获取元素。

/* Java program to print frequencies of all elements using 
   TreeMap */
import java.util.*;
 
class Main
{
    // This function prints frequencies of all elements
    static void printFreq(int arr[])
    {
        // Creates an empty TreeMap
        TreeMap<Integer, Integer> tmap =
                     new TreeMap<Integer, Integer>();
 
        // Traverse through the given array
        for (int i = 0; i < arr.length; i++)
        {
            Integer c = tmap.get(arr[i]);
 
            // If this is first occurrence of element   
            if (tmap.get(arr[i]) == null)
               tmap.put(arr[i], 1);
 
            // If elements already exists in hash map
            else
              tmap.put(arr[i], ++c);
        }
 
        // Print result
        for (Map.Entry m:tmap.entrySet())
          System.out.println("Frequency of " + m.getKey() + 
                             " is " + m.getValue());
    }
 
    // Driver method to test above method
    public static void main (String[] args)
    {
        int arr[] = {10, 34, 5, 10, 3, 5, 10};
        printFreq(arr);
    }
}

输出:

3 的频率为 1 
5 的频率为 2 
10 的频率为 3 
34 的频率为 1

关键点

    1、对于添加、删除、containsKey 等操作,时间复杂度为 O(log n,其中 n 是 TreeMap 中存在的元素数量。

    2、TreeMap 始终保持元素按排序(递增)顺序排列,而 HashMap 中的元素则无序。TreeMap 还提供了键的 first、last、floor 和 ceiling 等一些很酷的方法。

HashMap和TreeMap的区别:

HashMapTreeMap
1.它没有为元素提供任何顺序。它为元素提供顺序。
2.它的速度很快。它的速度很慢。
3.它允许一个键为空,也允许多个值。它不允许键为空,但允许多个空值。
4.它消耗更多的内存空间。它消耗更少的内存空间。
5.它仅具有基本功能。它具有先进的功能。
6.为了比较键,使用 equals()。为了比较键,使用 compare 或 compareTo()。
7.它的复杂度是O(1)。它的复杂度是O(log n)。

概述:

    1、HashMap 实现 Map 接口,而 TreeMap 实现 SortedMap 接口。Sorted Map 接口是 Map 的子接口。

    2、HashMap 实现哈希,而 TreeMap 实现红黑树(一种自平衡二叉搜索树)。因此,哈希和平衡二叉搜索树之间的所有差异都适用于此。

    3、HashMap 和 TreeMap 都有对应的 HashSet 和 TreeSet。HashSet 和 TreeSet 实现Set 接口。在 HashSet 和 TreeSet 中,我们只有键,没有值,它们主要用于查看集合中的存在/不存在。对于上述问题,我们不能使用 HashSet(或 TreeSet),因为我们无法存储计数。我们更喜欢 HashSet(或 TreeSet)而不是 HashMap(或 TreeMap)的一个示例问题是打印数组中的所有不同元素。

相关文章

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

hefeng_aspnet

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值