diff --git a/CHANGELOG.md b/CHANGELOG.md
index 9651cee1e..73dac269f 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -8,6 +8,7 @@
### 新特性
* 【extra 】 JschUtil增加execByShell方法(issue#I1CYES@Gitee)
* 【core 】 StrUtil增加subBetweenAll方法,Console增加where和lineNumber方法(issue#812@Github)
+* 【core 】 TableMap增加getKeys和getValues方法
### Bug修复
* 【extra 】 修复SpringUtil使用devtools重启报错问题
diff --git a/hutool-core/src/main/java/cn/hutool/core/collection/CollUtil.java b/hutool-core/src/main/java/cn/hutool/core/collection/CollUtil.java
index 3cb0ee020..186caf969 100644
--- a/hutool-core/src/main/java/cn/hutool/core/collection/CollUtil.java
+++ b/hutool-core/src/main/java/cn/hutool/core/collection/CollUtil.java
@@ -1310,6 +1310,30 @@ public class CollUtil {
return count;
}
+ /**
+ * 获取匹配规则定义中匹配到元素的所有位置
+ * 此方法对于某些无序集合的位置信息,以转换为数组后的位置为准。
+ *
+ * @param 元素类型
+ * @param collection 集合
+ * @param matcher 匹配器,为空则全部匹配
+ * @return 位置数组
+ * @since 5.2.5
+ */
+ public static int[] indexOfAll(Collection collection, Matcher matcher){
+ final List indexList = new ArrayList<>();
+ if (null != collection) {
+ int index = 0;
+ for (T t : collection) {
+ if (null == matcher || matcher.match(t)) {
+ indexList.add(index);
+ }
+ index++;
+ }
+ }
+ return Convert.convert(int[].class, indexList);
+ }
+
// ---------------------------------------------------------------------- isEmpty
/**
diff --git a/hutool-core/src/main/java/cn/hutool/core/collection/ListUtil.java b/hutool-core/src/main/java/cn/hutool/core/collection/ListUtil.java
index d45d2c60d..5579dcec9 100644
--- a/hutool-core/src/main/java/cn/hutool/core/collection/ListUtil.java
+++ b/hutool-core/src/main/java/cn/hutool/core/collection/ListUtil.java
@@ -2,7 +2,9 @@ package cn.hutool.core.collection;
import cn.hutool.core.comparator.PinyinComparator;
import cn.hutool.core.comparator.PropertyComparator;
+import cn.hutool.core.convert.Convert;
import cn.hutool.core.lang.Editor;
+import cn.hutool.core.lang.Matcher;
import cn.hutool.core.util.ArrayUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.PageUtil;
@@ -419,4 +421,27 @@ public class ListUtil {
}
return list2;
}
+
+ /**
+ * 获取匹配规则定义中匹配到元素的所有位置
+ *
+ * @param 元素类型
+ * @param list 列表
+ * @param matcher 匹配器,为空则全部匹配
+ * @return 位置数组
+ * @since 5.2.5
+ */
+ public static int[] indexOfAll(List list, Matcher matcher){
+ final List indexList = new ArrayList<>();
+ if (null != list) {
+ int index = 0;
+ for (T t : list) {
+ if (null == matcher || matcher.match(t)) {
+ indexList.add(index);
+ }
+ index++;
+ }
+ }
+ return Convert.convert(int[].class, indexList);
+ }
}
diff --git a/hutool-core/src/main/java/cn/hutool/core/map/TableMap.java b/hutool-core/src/main/java/cn/hutool/core/map/TableMap.java
index 7b4be3645..b80ec2ed0 100644
--- a/hutool-core/src/main/java/cn/hutool/core/map/TableMap.java
+++ b/hutool-core/src/main/java/cn/hutool/core/map/TableMap.java
@@ -1,13 +1,22 @@
package cn.hutool.core.map;
-import java.io.Serializable;
-import java.util.*;
-
import cn.hutool.core.collection.CollUtil;
+import cn.hutool.core.collection.ListUtil;
import cn.hutool.core.util.ArrayUtil;
+import cn.hutool.core.util.ObjectUtil;
+
+import java.io.Serializable;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Objects;
+import java.util.Set;
/**
- * 无重复键的Map
+ * 可重复键的Map
*
* @author looly
*
@@ -73,6 +82,34 @@ public class TableMap implements Map, Serializable {
return null;
}
+ /**
+ * 获取指定key对应的所有值
+ *
+ * @param key 键
+ * @return 值列表
+ * @since 5.2.5
+ */
+ public List getValues(K key){
+ return CollUtil.getAny(
+ this.values,
+ ListUtil.indexOfAll(this.keys, (ele)-> ObjectUtil.equal(ele, key))
+ );
+ }
+
+ /**
+ * 获取指定value对应的所有key
+ *
+ * @param value 值
+ * @return 值列表
+ * @since 5.2.5
+ */
+ public List getKeys(V value){
+ return CollUtil.getAny(
+ this.keys,
+ ListUtil.indexOfAll(this.values, (ele)-> ObjectUtil.equal(ele, value))
+ );
+ }
+
@Override
public V put(K key, V value) {
keys.add(key);
@@ -106,16 +143,19 @@ public class TableMap implements Map, Serializable {
values.clear();
}
+ @SuppressWarnings("NullableProblems")
@Override
public Set keySet() {
return new HashSet<>(keys);
}
+ @SuppressWarnings("NullableProblems")
@Override
public Collection values() {
- return new HashSet<>(values);
+ return Collections.unmodifiableList(this.values);
}
+ @SuppressWarnings("NullableProblems")
@Override
public Set> entrySet() {
HashSet> hashSet = new HashSet<>();
diff --git a/hutool-core/src/test/java/cn/hutool/core/collection/ListUtilTest.java b/hutool-core/src/test/java/cn/hutool/core/collection/ListUtilTest.java
index 36ce84875..61aa2855c 100644
--- a/hutool-core/src/test/java/cn/hutool/core/collection/ListUtilTest.java
+++ b/hutool-core/src/test/java/cn/hutool/core/collection/ListUtilTest.java
@@ -15,4 +15,13 @@ public class ListUtilTest {
Assert.assertEquals("edit2", filter.get(1));
Assert.assertEquals("edit3", filter.get(2));
}
+
+ @Test
+ public void indexOfAll() {
+ List a = ListUtil.toLinkedList("1", "2", "3", "4", "3", "2", "1");
+ final int[] indexArray = ListUtil.indexOfAll(a, "2"::equals);
+ Assert.assertArrayEquals(new int[]{1,5}, indexArray);
+ final int[] indexArray2 = ListUtil.indexOfAll(a, "1"::equals);
+ Assert.assertArrayEquals(new int[]{0,6}, indexArray2);
+ }
}