TreeMap.putAll has undocumented behavior which has different side effect based on parameter

Sean Chou zhouyx at
Mon Oct 15 03:50:12 UTC 2012

Hi all,

    It is found TreeMap.putAll method may or may not invoke
TreeMap.put method based on parameter. If TreeMap is extended and the
put method is override, it may behave different from what is expected.
  This behavior should be documented.

    The following test case tries to putAll a hashamp and a treemap in
a class extended from TreeMap.

/////////////// Testcase ////////////////////
 * Copyright (c) 2012 Oracle and/or its affiliates. All rights reserved.
 * This code is free software; you can redistribute it and/or modify it
 * under the terms of the GNU General Public License version 2 only, as
 * published by the Free Software Foundation.
 * This code is distributed in the hope that it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
 * version 2 for more details (a copy is included in the LICENSE file that
 * accompanied this code).
 * You should have received a copy of the GNU General Public License version
 * 2 along with this work; if not, write to the Free Software Foundation,
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 * or visit if you need additional information or have any
 * questions.

 * Portions Copyright (c) 2012 IBM Corporation

import java.util.HashMap;
import java.util.TreeMap;

public class TreeMapTest {

    static class MyTreeMap extends TreeMap<String, String> {
        public String put(String key, String value) {
            System.out.println("Override put is invoked in MyTreeMap");
            return super.put(key, value);

    public static void main(String[] args) {
        TreeMap<String, String> tm = new TreeMap<>();
        tm.put("treeMap", "treeMap");

        HashMap<String, String> hm = new HashMap<>();
        hm.put("hashMap", "hashMap");

        System.out.println("Test started, the override put method in
MyTreeMap " +
        		            "is not invoked when putAll a TreeMap, but " +
        		            "it is invoked when putAll a HashMap");

        TreeMap<String, String> treeMap = new MyTreeMap();
        TreeMap<String, String> treeMap2 = new MyTreeMap();

        System.out.println("putAll treemap:");
        System.out.println("putAll hashmap:");


Best Regards,
Sean Chou

More information about the core-libs-dev mailing list