001/* 002 * Licensed to the Apache Software Foundation (ASF) under one or more 003 * contributor license agreements. See the NOTICE file distributed with 004 * this work for additional information regarding copyright ownership. 005 * The ASF licenses this file to You under the Apache License, Version 2.0 006 * (the "License"); you may not use this file except in compliance with 007 * the License. You may obtain a copy of the License at 008 * 009 * https://www.apache.org/licenses/LICENSE-2.0 010 * 011 * Unless required by applicable law or agreed to in writing, software 012 * distributed under the License is distributed on an "AS IS" BASIS, 013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 014 * See the License for the specific language governing permissions and 015 * limitations under the License. 016 */ 017package org.apache.commons.collections4.keyvalue; 018 019import java.util.Map; 020import java.util.Map.Entry; 021import java.util.Objects; 022 023import org.apache.commons.collections4.KeyValue; 024 025/** 026 * A mutable {@code KeyValue} pair that does not implement 027 * {@link Entry Map.Entry}. 028 * <p> 029 * Note that a {@code DefaultKeyValue} instance may not contain 030 * itself as a key or value. 031 * </p> 032 * 033 * @param <K> The type of keys 034 * @param <V> The type of values 035 * @since 3.0 036 */ 037public class DefaultKeyValue<K, V> extends AbstractKeyValue<K, V> { 038 039 /** 040 * Constructs a new pair with a null key and null value. 041 */ 042 public DefaultKeyValue() { 043 super(null, null); 044 } 045 046 /** 047 * Constructs a new pair with the specified key and given value. 048 * 049 * @param key The key for the entry, may be null 050 * @param value The value for the entry, may be null 051 */ 052 public DefaultKeyValue(final K key, final V value) { 053 super(key, value); 054 } 055 056 /** 057 * Constructs a new pair from the specified {@code KeyValue}. 058 * 059 * @param pair The pair to copy, must not be null 060 * @throws NullPointerException if the entry is null 061 */ 062 public DefaultKeyValue(final KeyValue<? extends K, ? extends V> pair) { 063 super(pair.getKey(), pair.getValue()); 064 } 065 066 /** 067 * Constructs a new pair from the specified {@code Map.Entry}. 068 * 069 * @param entry The entry to copy, must not be null 070 * @throws NullPointerException if the entry is null 071 */ 072 public DefaultKeyValue(final Map.Entry<? extends K, ? extends V> entry) { 073 super(entry.getKey(), entry.getValue()); 074 } 075 076 /** 077 * Compares this {@code Map.Entry} with another {@code Map.Entry}. 078 * <p> 079 * Returns true if the compared object is also a {@code DefaultKeyValue}, 080 * and its key and value are equal to this object's key and value. 081 * 082 * @param obj The object to compare to 083 * @return true if equal key and value 084 */ 085 @Override 086 public boolean equals(final Object obj) { 087 if (obj == this) { 088 return true; 089 } 090 if (!(obj instanceof DefaultKeyValue)) { 091 return false; 092 } 093 094 final DefaultKeyValue<?, ?> other = (DefaultKeyValue<?, ?>) obj; 095 return 096 Objects.equals(getKey(), other.getKey()) && 097 Objects.equals(getValue(), other.getValue()); 098 } 099 100 /** 101 * Gets a hashCode compatible with the equals method. 102 * <p> 103 * Implemented per API documentation of {@link java.util.Map.Entry#hashCode()}, 104 * however subclasses may override this. 105 * 106 * @return A suitable hash code 107 */ 108 @Override 109 public int hashCode() { 110 return (getKey() == null ? 0 : getKey().hashCode()) ^ 111 (getValue() == null ? 0 : getValue().hashCode()); 112 } 113 114 /** 115 * Sets the key. 116 * 117 * @param key The new key 118 * @return The old key 119 * @throws IllegalArgumentException if key is this object 120 */ 121 @Override 122 public K setKey(final K key) { 123 if (key == this) { 124 throw new IllegalArgumentException("DefaultKeyValue may not contain itself as a key."); 125 } 126 127 return super.setKey(key); 128 } 129 130 /** 131 * Sets the value. 132 * 133 * @return The old value of the value 134 * @param value The new value 135 * @throws IllegalArgumentException if value is this object 136 */ 137 @Override 138 public V setValue(final V value) { 139 if (value == this) { 140 throw new IllegalArgumentException("DefaultKeyValue may not contain itself as a value."); 141 } 142 143 return super.setValue(value); 144 } 145 146 /** 147 * Returns a new {@code Map.Entry} object with key and value from this pair. 148 * 149 * @return A MapEntry instance 150 */ 151 public Map.Entry<K, V> toMapEntry() { 152 return new DefaultMapEntry<>(this); 153 } 154 155}