Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/398.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java `用于按索引获取项的HashMap`或LinkedHashMap`的ArrayList_Java_Collections - Fatal编程技术网

Java `用于按索引获取项的HashMap`或LinkedHashMap`的ArrayList

Java `用于按索引获取项的HashMap`或LinkedHashMap`的ArrayList,java,collections,Java,Collections,我需要以键值形式存储大量数据。 另外,我有两个要求 通过索引查询数据,如从数组查询数据 因此,必须保留数据结构中的顺序 对于要求2-我可以使用 对于要求1,我有两个选择: 1.1 |实现HashMap的数组列表。[ArrayList] 1.2 |实现LinkedHashMap并使用 ->newarraylist(hashMapObject.entrySet()).get(0) 问题是1.1或1.2中哪个更好 我说的更好,是指在内存和空间方面效率更高。 public class HashM

我需要以键值形式存储大量数据。 另外,我有两个要求

  • 通过索引查询数据,如从数组查询数据
  • 因此,必须保留数据结构中的顺序 对于要求2-我可以使用

    对于要求1,我有两个选择:

    • 1.1 |实现HashMap的数组列表。[
      ArrayList
      ]
    • 1.2 |实现LinkedHashMap并使用
      • ->
        newarraylist(hashMapObject.entrySet()).get(0)
    问题是
    1.1
    1.2
    中哪个更好

    我说的更好,是指在内存和空间方面效率更高。

    public class HashMapVsArrayOfHashMap {
    
        public static void main(String[] args){
            ArrayList<HashMap<String, String>> listOfMaps=new ArrayList<HashMap<String,String>>();
            for( int i=0;i<1000;i++){
                final int finalI=i;
            listOfMaps.add(new HashMap<String, String>(){{put("asdfasdfasdfasdfadsf"+finalI,"asdfsdafasdfsadfasdf"+finalI);}});
            }
            LinkedHashMap<String, String> map=new LinkedHashMap<String, String>();
            for(int i=0;i<1000;i++)
                map.put("asdfasdfasdfasdfadsf"+i,"asdfsdafasdfsadfasdf"+i);     
            int position=700;
            testArrayList("Method1:ArrayListOfHashMaps",position,listOfMaps);
            testHashMap("Method2:LinkedHashMap",position,map);
        }
    
        private static void testArrayList(String string, int position,
                ArrayList<HashMap<String, String>> listOfMaps) {
            long start, end;
            start=System.nanoTime();
            listOfMaps.get(position).get("asdfasdfasdfasdfadsf"+position);
            end=System.nanoTime();
            System.out.println(string+"|Difference = "+(end-start));        
        }
        private static void testHashMap(String string, int position,
                LinkedHashMap<String, String> map) {
            long start, end;
            start=System.nanoTime();
    
            String s= new ArrayList<String>(map.keySet()).get(position);
    
            end=System.nanoTime();
            System.out.println(string+"|Difference = "+(end-start));        
        }
    }
    
    让我们假设数据量大约为50到100个键值对,字符串大小平均-假设每个键值为10-30个字符,值为30-50个字符。

    尝试使用SortedMap

    例如:

    SortedMap<Key, Value> map = new TreeMap<Key, Value>();
    
    List<MyValue> list = new ArrayList<MyValue>(100000);
    Map<MyKey,MyValue> map = new HashMap<MyKey,MyValue>(100000);
    
    while(moreItems) {
        // read input
        MyKey key = ...
        MyValue value = ...
        list.add(value);
        map.put(key,value);
    }
    
    // lookup by index
    MyValue v1 = list.get(11241);
    // lookup by key
    MyValue v2 = map.get(someKey);
    
    我最近用它们分析了1000万条推特,其中关键是日期,值是计数器。我想保持日期的顺序


    更新如果您只需对数据进行编辑即可,那么我的方法就足够了。也许你可以举个小例子?如果绝对需要您也可以通过索引引用数据,那么您似乎只需要维护两个数据结构,如@Jim所述。我以前不得不这么做。

    尝试使用SortedMap

    例如:

    SortedMap<Key, Value> map = new TreeMap<Key, Value>();
    
    List<MyValue> list = new ArrayList<MyValue>(100000);
    Map<MyKey,MyValue> map = new HashMap<MyKey,MyValue>(100000);
    
    while(moreItems) {
        // read input
        MyKey key = ...
        MyValue value = ...
        list.add(value);
        map.put(key,value);
    }
    
    // lookup by index
    MyValue v1 = list.get(11241);
    // lookup by key
    MyValue v2 = map.get(someKey);
    
    我最近用它们分析了1000万条推特,其中关键是日期,值是计数器。我想保持日期的顺序


    更新如果您只需对数据进行编辑即可,那么我的方法就足够了。也许你可以举个小例子?如果绝对需要您也可以通过索引引用数据,那么您似乎只需要维护两个数据结构,如@Jim所述。我以前不得不这么做。

    我认为LinkedHashMap是最好的解决方案,但是要获得物品,你可以使用

    hashMapObject.values().toArray()[index]
    
    但是,toArray方法对于大量数据来说速度较慢。但这是你必须测试的


    如果速度确实是一个问题,那么您可以维护一个HashMap和一个ArrayList。

    我认为LinkedHashMap是最好的解决方案,但是要获取项目,您可以使用

    hashMapObject.values().toArray()[index]
    
    但是,toArray方法对于大量数据来说速度较慢。但这是你必须测试的


    如果速度确实是一个问题,您可以维护一个HashMap和一个ArrayList。

    请记住,集合不包含对象,只包含对对象的引用

    使用两个集合:

  • 一个
    ArrayList
    ,用于存储引用以便按索引访问
  • 一个
    HashMap
    来存储引用,以便按键访问
  • 例如:

    SortedMap<Key, Value> map = new TreeMap<Key, Value>();
    
    List<MyValue> list = new ArrayList<MyValue>(100000);
    Map<MyKey,MyValue> map = new HashMap<MyKey,MyValue>(100000);
    
    while(moreItems) {
        // read input
        MyKey key = ...
        MyValue value = ...
        list.add(value);
        map.put(key,value);
    }
    
    // lookup by index
    MyValue v1 = list.get(11241);
    // lookup by key
    MyValue v2 = map.get(someKey);
    

    请记住,集合不包含对象,只包含对对象的引用

    使用两个集合:

  • 一个
    ArrayList
    ,用于存储引用以便按索引访问
  • 一个
    HashMap
    来存储引用,以便按键访问
  • 例如:

    SortedMap<Key, Value> map = new TreeMap<Key, Value>();
    
    List<MyValue> list = new ArrayList<MyValue>(100000);
    Map<MyKey,MyValue> map = new HashMap<MyKey,MyValue>(100000);
    
    while(moreItems) {
        // read input
        MyKey key = ...
        MyValue value = ...
        list.add(value);
        map.put(key,value);
    }
    
    // lookup by index
    MyValue v1 = list.get(11241);
    // lookup by key
    MyValue v2 = map.get(someKey);
    

    我自己去做实验。结果表明,使用1000个元素创建HashMaps数组列表的方法要快40倍。

    public class HashMapVsArrayOfHashMap {
    
        public static void main(String[] args){
            ArrayList<HashMap<String, String>> listOfMaps=new ArrayList<HashMap<String,String>>();
            for( int i=0;i<1000;i++){
                final int finalI=i;
            listOfMaps.add(new HashMap<String, String>(){{put("asdfasdfasdfasdfadsf"+finalI,"asdfsdafasdfsadfasdf"+finalI);}});
            }
            LinkedHashMap<String, String> map=new LinkedHashMap<String, String>();
            for(int i=0;i<1000;i++)
                map.put("asdfasdfasdfasdfadsf"+i,"asdfsdafasdfsadfasdf"+i);     
            int position=700;
            testArrayList("Method1:ArrayListOfHashMaps",position,listOfMaps);
            testHashMap("Method2:LinkedHashMap",position,map);
        }
    
        private static void testArrayList(String string, int position,
                ArrayList<HashMap<String, String>> listOfMaps) {
            long start, end;
            start=System.nanoTime();
            listOfMaps.get(position).get("asdfasdfasdfasdfadsf"+position);
            end=System.nanoTime();
            System.out.println(string+"|Difference = "+(end-start));        
        }
        private static void testHashMap(String string, int position,
                LinkedHashMap<String, String> map) {
            long start, end;
            start=System.nanoTime();
    
            String s= new ArrayList<String>(map.keySet()).get(position);
    
            end=System.nanoTime();
            System.out.println(string+"|Difference = "+(end-start));        
        }
    }
    
    公共类HashMapVsArrayOfHashMap{
    公共静态void main(字符串[]args){
    ArrayList listOfMaps=新的ArrayList();
    
    对于(int i=0;i我自己进行了实验。结果表明,创建哈希映射的数组列表的方法在1000个元素的情况下大约快了40倍。

    public class HashMapVsArrayOfHashMap {
    
        public static void main(String[] args){
            ArrayList<HashMap<String, String>> listOfMaps=new ArrayList<HashMap<String,String>>();
            for( int i=0;i<1000;i++){
                final int finalI=i;
            listOfMaps.add(new HashMap<String, String>(){{put("asdfasdfasdfasdfadsf"+finalI,"asdfsdafasdfsadfasdf"+finalI);}});
            }
            LinkedHashMap<String, String> map=new LinkedHashMap<String, String>();
            for(int i=0;i<1000;i++)
                map.put("asdfasdfasdfasdfadsf"+i,"asdfsdafasdfsadfasdf"+i);     
            int position=700;
            testArrayList("Method1:ArrayListOfHashMaps",position,listOfMaps);
            testHashMap("Method2:LinkedHashMap",position,map);
        }
    
        private static void testArrayList(String string, int position,
                ArrayList<HashMap<String, String>> listOfMaps) {
            long start, end;
            start=System.nanoTime();
            listOfMaps.get(position).get("asdfasdfasdfasdfadsf"+position);
            end=System.nanoTime();
            System.out.println(string+"|Difference = "+(end-start));        
        }
        private static void testHashMap(String string, int position,
                LinkedHashMap<String, String> map) {
            long start, end;
            start=System.nanoTime();
    
            String s= new ArrayList<String>(map.keySet()).get(position);
    
            end=System.nanoTime();
            System.out.println(string+"|Difference = "+(end-start));        
        }
    }
    
    公共类HashMapVsArrayOfHashMap{
    公共静态void main(字符串[]args){
    ArrayList listOfMaps=新的ArrayList();
    
    对于(int i=0;i为什么不直接测量?测量是知道的。为什么它需要在Hashmap中?你不能只使用字符串对的arraylist吗?Hashmap是无序的集合,因此索引没有意义。如果你需要索引,你使用的集合是错误的。@VinayWadhwa我只是指存储包含2个str的对象的arraylist可以是自定义定义的对象,也可以是类似java.util.Map的对象。Entry@VinayWadhwa如果大多数KVP具有几乎相同的密钥集(例如,您最多有120个唯一密钥,KVP组使用120个密钥中的50..100个密钥的子集),那么您可以存储一个“模式”它将一个键映射到一个整数索引,然后存储120个对象的数组,其中一些对象为空。为什么不直接测量?测量就是知道。为什么它需要在Hashmap中?难道不能只使用字符串对的arraylist吗?Hashmap是无序集合,因此索引没有意义。如果需要索引,则使用wrong集合。@VinayWadhwa我指的是存储包含2个字符串的对象的ArrayList;可以是自定义定义的对象,也可以是类似java.util.Map的对象。Entry@VinayWadhwa如果大多数KVP都有几乎相同的密钥集(比如,您最多有120个唯一密钥,KVP组使用120个密钥中的50..100个密钥的子集),那么您可以存储“模式"它将一个键映射到一个整数索引,然后存储120个对象的数组,其中一些对象为空。你是说toArray方法为什么会慢?因为它会遍历HashMap中的所有对象。请参阅AbstractCollection#toArray你是说toArray方法为什么会慢?因为它会遍历HashMap中的所有对象。请参阅AbsTrackCollection#toArray“如果你只需要创建数据就可以了,那么我的方法就足够了”-在任何其他情况下会有什么不同?因为如果你必须直接索引数据结构,data[index],这通常意味着你需要随机访问数据。例如,读取索引14,然后读取10,然后读取1,然后读取13。不管需要多少次